From d0eec6097f79c7fb3ea8b5d8bb0dcca1da1f85a6 Mon Sep 17 00:00:00 2001 From: TheJackiMonster Date: Mon, 24 May 2021 01:30:17 +0200 Subject: -moved messenger service out of experimental Signed-off-by: TheJackiMonster -moved out of experimental, included protocol versions into ports and fixed byte-order of 32bit integers in messages Signed-off-by: TheJackiMonster --- src/Makefile.am | 4 +- src/include/gnunet_messenger_service.h | 21 ++++++++++ .../gnunet-service-messenger_list_messages.c | 2 +- .../gnunet-service-messenger_list_messages.h | 2 +- src/messenger/gnunet-service-messenger_room.c | 4 +- src/messenger/gnunet-service-messenger_tunnel.c | 4 +- src/messenger/messenger_api.c | 46 +++++++++++++++++++++- src/messenger/messenger_api_message.c | 18 ++++++--- src/messenger/messenger_api_room.c | 36 +++++++++++++++++ src/messenger/messenger_api_room.h | 11 ++++++ src/messenger/messenger_api_util.c | 16 ++++++++ src/messenger/messenger_api_util.h | 14 +++++++ 12 files changed, 165 insertions(+), 13 deletions(-) diff --git a/src/Makefile.am b/src/Makefile.am index 5fd00e3f5..07b9cf1e9 100644 --- a/src/Makefile.am +++ b/src/Makefile.am @@ -8,8 +8,7 @@ endif if HAVE_EXPERIMENTAL EXP_DIR = \ - rps \ - messenger + rps #abd FTBFS if HAVE_ABE EXP_DIR += \ @@ -101,5 +100,6 @@ SUBDIRS = \ pt \ secretsharing \ reclaim \ + messenger \ $(EXP_DIR) \ integration-tests diff --git a/src/include/gnunet_messenger_service.h b/src/include/gnunet_messenger_service.h index 0576e239f..ad5cc4f12 100644 --- a/src/include/gnunet_messenger_service.h +++ b/src/include/gnunet_messenger_service.h @@ -50,6 +50,8 @@ extern "C" { /** * Version number of GNUnet Messenger API. + * + * Current version of the Messenger: 0.1 */ #define GNUNET_MESSENGER_VERSION 0x00000001 @@ -219,6 +221,10 @@ struct GNUNET_MESSENGER_MessageInfo /** * The version of GNUnet Messenger API. + * + * The sixteen lower bits represent the lower version number while the sixteen higher bits + * represent the higher version number. A different higher version number implies imcompatibility + * to lower versions while differences in the lower version can still be supported potentially. */ uint32_t messenger_version; }; @@ -671,6 +677,21 @@ GNUNET_MESSENGER_enter_room (struct GNUNET_MESSENGER_Handle *handle, const struc void GNUNET_MESSENGER_close_room (struct GNUNET_MESSENGER_Room *room); +/** + * Searches for a specific contact in a given room and calls a selected callback with a given + * closure for each of them containing the contact as a member. The callback will receive a room matching the condition + * and the given contact. The function returns the amount of rooms iterated with the given callback. + * + * @param[in] handle Messenger handle to use + * @param[in] contact Contact handle + * @param[in] callback Function called for each room + * @param[in] cls Closure for the callback handler + * @return Amount of rooms iterated + */ +int +GNUNET_MESSENGER_find_rooms (const struct GNUNET_MESSENGER_Handle *handle, const struct GNUNET_MESSENGER_Contact *contact, + GNUNET_MESSENGER_MemberCallback callback, void *cls); + /** * Get the contact of a member in a room which sent a specific message identified with a given hash. * diff --git a/src/messenger/gnunet-service-messenger_list_messages.c b/src/messenger/gnunet-service-messenger_list_messages.c index bb6086e41..2666ccdab 100644 --- a/src/messenger/gnunet-service-messenger_list_messages.c +++ b/src/messenger/gnunet-service-messenger_list_messages.c @@ -125,7 +125,7 @@ load_list_messages (struct GNUNET_MESSENGER_ListMessages *messages, const char * } void -save_list_messages (struct GNUNET_MESSENGER_ListMessages *messages, const char *path) +save_list_messages (const struct GNUNET_MESSENGER_ListMessages *messages, const char *path) { GNUNET_assert((messages) && (path)); diff --git a/src/messenger/gnunet-service-messenger_list_messages.h b/src/messenger/gnunet-service-messenger_list_messages.h index 9ace84cbf..93ec203ea 100644 --- a/src/messenger/gnunet-service-messenger_list_messages.h +++ b/src/messenger/gnunet-service-messenger_list_messages.h @@ -104,6 +104,6 @@ load_list_messages (struct GNUNET_MESSENGER_ListMessages *messages, const char * * @param[in] path Path of file */ void -save_list_messages (struct GNUNET_MESSENGER_ListMessages *messages, const char *path); +save_list_messages (const struct GNUNET_MESSENGER_ListMessages *messages, const char *path); #endif //GNUNET_SERVICE_MESSENGER_LIST_MESSAGES_H diff --git a/src/messenger/gnunet-service-messenger_room.c b/src/messenger/gnunet-service-messenger_room.c index e8fe5b1f3..c3a5e3a4b 100644 --- a/src/messenger/gnunet-service-messenger_room.c +++ b/src/messenger/gnunet-service-messenger_room.c @@ -329,7 +329,9 @@ open_room (struct GNUNET_MESSENGER_SrvRoom *room, struct GNUNET_MESSENGER_SrvHan struct GNUNET_MessageHeader, NULL), GNUNET_MQ_handler_end() }; - room->port = GNUNET_CADET_open_port (cadet, key, callback_room_connect, room, NULL, callback_tunnel_disconnect, + struct GNUNET_HashCode port; + convert_messenger_key_to_port(key, &port); + room->port = GNUNET_CADET_open_port (cadet, &port, callback_room_connect, room, NULL, callback_tunnel_disconnect, handlers); if (room->port) diff --git a/src/messenger/gnunet-service-messenger_tunnel.c b/src/messenger/gnunet-service-messenger_tunnel.c index 80d8dfa5e..b9d063813 100644 --- a/src/messenger/gnunet-service-messenger_tunnel.c +++ b/src/messenger/gnunet-service-messenger_tunnel.c @@ -235,7 +235,9 @@ connect_tunnel (struct GNUNET_MESSENGER_SrvTunnel *tunnel) struct GNUNET_MessageHeader, NULL), GNUNET_MQ_handler_end() }; - tunnel->channel = GNUNET_CADET_channel_create (cadet, tunnel, door, key, NULL, callback_tunnel_disconnect, handlers); + struct GNUNET_HashCode port; + convert_messenger_key_to_port(key, &port); + tunnel->channel = GNUNET_CADET_channel_create (cadet, tunnel, door, &port, NULL, callback_tunnel_disconnect, handlers); return GNUNET_YES; } diff --git a/src/messenger/messenger_api.c b/src/messenger/messenger_api.c index b42bb40cc..0536a3154 100644 --- a/src/messenger/messenger_api.c +++ b/src/messenger/messenger_api.c @@ -574,6 +574,50 @@ GNUNET_MESSENGER_close_room (struct GNUNET_MESSENGER_Room *room) send_close_room (room->handle, room); } +struct GNUNET_MESSENGER_RoomFind +{ + struct GNUNET_MESSENGER_Contact *contact; + GNUNET_MESSENGER_MemberCallback callback; + size_t counter; + void *cls; +}; + +static int +iterate_find_room (void* cls, const struct GNUNET_HashCode *key, void *value) +{ + struct GNUNET_MESSENGER_RoomFind *find = cls; + struct GNUNET_MESSENGER_Room *room = value; + + if ((find->counter > 0) && ((!find->contact) || (GNUNET_YES == find_room_member(room, find->contact)))) + { + find->counter--; + + if (!find->callback) + return GNUNET_YES; + + return find->callback(find->cls, room, find->contact); + } + else + return GNUNET_NO; +} + +int +GNUNET_MESSENGER_find_rooms (const struct GNUNET_MESSENGER_Handle *handle, const struct GNUNET_MESSENGER_Contact *contact, + GNUNET_MESSENGER_MemberCallback callback, void *cls) +{ + if (!handle) + return GNUNET_SYSERR; + + struct GNUNET_MESSENGER_RoomFind find; + + find.contact = contact; + find.callback = callback; + find.counter = (contact? contact->rc : SIZE_MAX); + find.cls = cls; + + return GNUNET_CONTAINER_multihashmap_iterate(handle->rooms, iterate_find_room, &find); +} + struct GNUNET_MESSENGER_Contact* GNUNET_MESSENGER_get_sender (const struct GNUNET_MESSENGER_Room *room, const struct GNUNET_HashCode *hash) { @@ -693,7 +737,7 @@ GNUNET_MESSENGER_get_message (const struct GNUNET_MESSENGER_Room *room, const st int GNUNET_MESSENGER_iterate_members (struct GNUNET_MESSENGER_Room *room, GNUNET_MESSENGER_MemberCallback callback, - void* cls) + void *cls) { if (!room) return GNUNET_SYSERR; diff --git a/src/messenger/messenger_api_message.c b/src/messenger/messenger_api_message.c index d65b80576..facd7b093 100644 --- a/src/messenger/messenger_api_message.c +++ b/src/messenger/messenger_api_message.c @@ -373,11 +373,14 @@ static void encode_message_body (enum GNUNET_MESSENGER_MessageKind kind, const struct GNUNET_MESSENGER_MessageBody *body, uint16_t length, char *buffer, uint16_t offset) { + uint32_t version; switch (kind) { case GNUNET_MESSENGER_KIND_INFO: + version = GNUNET_htobe32(body->info.messenger_version); + encode_step_key(buffer, offset, &(body->info.host_key), length); - encode_step(buffer, offset, &(body->info.messenger_version)); + encode_step(buffer, offset, &version); break; case GNUNET_MESSENGER_KIND_JOIN: encode_step_key(buffer, offset, &(body->join.key), length); @@ -452,7 +455,7 @@ encode_message (const struct GNUNET_MESSENGER_Message *message, uint16_t length, if (GNUNET_YES == include_signature) encode_step_signature(buffer, offset, &(message->header.signature), length); - const kind_t kind = (kind_t) message->header.kind; + const kind_t kind = GNUNET_htobe32((kind_t) message->header.kind); encode_step(buffer, offset, &(message->header.timestamp)); encode_step(buffer, offset, &(message->header.sender_id)); @@ -468,7 +471,7 @@ encode_short_message (const struct GNUNET_MESSENGER_ShortMessage *message, uint1 struct GNUNET_HashCode hash; uint16_t offset = sizeof(hash); - const kind_t kind = (kind_t) message->kind; + const kind_t kind = GNUNET_htobe32((kind_t) message->kind); encode_step(buffer, offset, &kind); @@ -526,11 +529,14 @@ decode_message_body (enum GNUNET_MESSENGER_MessageKind *kind, struct GNUNET_MESS length -= padding; + uint32_t version; switch (*kind) { case GNUNET_MESSENGER_KIND_INFO: { decode_step_key(buffer, offset, &(body->info.host_key), length); - decode_step(buffer, offset, &(body->info.messenger_version)); + decode_step(buffer, offset, &version); + + body->info.messenger_version = GNUNET_be32toh(version); break; } case GNUNET_MESSENGER_KIND_JOIN: { decode_step_key(buffer, offset, &(body->join.key), length); @@ -618,7 +624,7 @@ decode_message (struct GNUNET_MESSENGER_Message *message, uint16_t length, const decode_step(buffer, offset, &(message->header.previous)); decode_step(buffer, offset, &kind); - message->header.kind = (enum GNUNET_MESSENGER_MessageKind) kind; + message->header.kind = (enum GNUNET_MESSENGER_MessageKind) GNUNET_be32toh(kind); if (count < get_message_kind_size (message->header.kind)) return GNUNET_NO; @@ -655,7 +661,7 @@ decode_short_message (struct GNUNET_MESSENGER_ShortMessage *message, uint16_t le decode_step(buffer, offset, &kind); - message->kind = (enum GNUNET_MESSENGER_MessageKind) kind; + message->kind = (enum GNUNET_MESSENGER_MessageKind) GNUNET_be32toh(kind); if (length < get_short_message_size (message, GNUNET_NO)) return GNUNET_NO; diff --git a/src/messenger/messenger_api_room.c b/src/messenger/messenger_api_room.c index 5b7edee60..6779984bd 100644 --- a/src/messenger/messenger_api_room.c +++ b/src/messenger/messenger_api_room.c @@ -305,3 +305,39 @@ iterate_room_members (struct GNUNET_MESSENGER_Room *room, GNUNET_MESSENGER_Membe return GNUNET_CONTAINER_multishortmap_iterate(room->members, iterate_local_members, &call); } + +struct GNUNET_MESSENGER_MemberFind +{ + struct GNUNET_MESSENGER_Contact *contact; + int result; +}; + +static int +iterate_find_member (void* cls, const struct GNUNET_ShortHashCode *key, void *value) +{ + struct GNUNET_MESSENGER_MemberFind *find = cls; + struct GNUNET_MESSENGER_Contact *contact = value; + + if (contact == find->contact) + { + find->result = GNUNET_YES; + return GNUNET_NO; + } + + return GNUNET_YES; +} + +int +find_room_member (const struct GNUNET_MESSENGER_Room *room, const struct GNUNET_MESSENGER_Contact *contact) +{ + GNUNET_assert(room); + + struct GNUNET_MESSENGER_MemberFind find; + + find.contact = contact; + find.result = GNUNET_NO; + + GNUNET_CONTAINER_multishortmap_iterate(room->members, iterate_find_member, &find); + + return find.result; +} diff --git a/src/messenger/messenger_api_room.h b/src/messenger/messenger_api_room.h index eb41cf740..634052272 100644 --- a/src/messenger/messenger_api_room.h +++ b/src/messenger/messenger_api_room.h @@ -126,4 +126,15 @@ int iterate_room_members (struct GNUNET_MESSENGER_Room *room, GNUNET_MESSENGER_MemberCallback callback, void* cls); +/** + * Checks through all members of a given room if a specific contact is found and + * returns a result depending on that. + * + * @param[in] room Room + * @param[in] contact + * @return #GNUNET_YES if found, otherwise #GNUNET_NO + */ +int +find_room_member (const struct GNUNET_MESSENGER_Room *room, const struct GNUNET_MESSENGER_Contact *contact); + #endif //GNUNET_MESSENGER_API_ROOM_H diff --git a/src/messenger/messenger_api_util.c b/src/messenger/messenger_api_util.c index 68e15d789..4ad00c45e 100644 --- a/src/messenger/messenger_api_util.c +++ b/src/messenger/messenger_api_util.c @@ -82,3 +82,19 @@ get_anonymous_public_key () return &public_key; } + +void +convert_messenger_key_to_port(const struct GNUNET_HashCode *key, struct GNUNET_HashCode *port) +{ + static uint32_t version_value = 0; + static struct GNUNET_HashCode version; + + if (!version_value) { + version_value = (uint32_t) (GNUNET_MESSENGER_VERSION); + version_value = ((version_value >> 16) & 0xFFFF); + version_value = GNUNET_htole32(version_value); + GNUNET_CRYPTO_hash(&version_value, sizeof(version_value), &version); + } + + GNUNET_CRYPTO_hash_sum(key, &version, port); +} diff --git a/src/messenger/messenger_api_util.h b/src/messenger/messenger_api_util.h index c70a3601f..af562a1e8 100644 --- a/src/messenger/messenger_api_util.h +++ b/src/messenger/messenger_api_util.h @@ -32,6 +32,7 @@ #include "gnunet_crypto_lib.h" #include "gnunet_disk_lib.h" #include "gnunet_identity_service.h" +#include "gnunet_messenger_service.h" /** * Starts an urgent task to close a CADET channel asynchronously. @@ -61,4 +62,17 @@ generate_free_member_id (struct GNUNET_ShortHashCode *id, const struct GNUNET_CO const struct GNUNET_IDENTITY_PublicKey* get_anonymous_public_key (); +/** + * Converts a Messenger service key of a room to the specific port which + * gets used for the CADET channels. + * + * The port includes upper bits of the #GNUNET_MESSENGER_VERSION to + * reduce the chance of incompatible connections. + * + * @param[in] key Messenger service room key + * @param[out] port CADET service port + */ +void +convert_messenger_key_to_port(const struct GNUNET_HashCode *key, struct GNUNET_HashCode *port); + #endif //GNUNET_SERVICE_MESSENGER_UTIL_H -- cgit v1.2.3