summaryrefslogtreecommitdiff
path: root/src/messenger/gnunet-service-messenger_service.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/messenger/gnunet-service-messenger_service.c')
-rw-r--r--src/messenger/gnunet-service-messenger_service.c516
1 files changed, 0 insertions, 516 deletions
diff --git a/src/messenger/gnunet-service-messenger_service.c b/src/messenger/gnunet-service-messenger_service.c
deleted file mode 100644
index 963314fd8..000000000
--- a/src/messenger/gnunet-service-messenger_service.c
+++ /dev/null
@@ -1,516 +0,0 @@
-/*
- This file is part of GNUnet.
- Copyright (C) 2020 GNUnet e.V.
-
- GNUnet is free software: you can redistribute it and/or modify it
- under the terms of the GNU Affero General Public License as published
- by the Free Software Foundation, either version 3 of the License,
- 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
- Affero General Public License for more details.
-
- You should have received a copy of the GNU Affero General Public License
- along with this program. If not, see <http://www.gnu.org/licenses/>.
-
- SPDX-License-Identifier: AGPL3.0-or-later
- */
-/**
- * @author Tobias Frisch
- * @file src/messenger/gnunet-service-messenger_service.c
- * @brief GNUnet MESSENGER service
- */
-
-#include "gnunet-service-messenger_service.h"
-
-#include "gnunet-service-messenger_message_kind.h"
-
-#include "gnunet-service-messenger.h"
-#include "gnunet-service-messenger_util.h"
-
-static void
-callback_shutdown_service (void *cls)
-{
- struct GNUNET_MESSENGER_Service *service = cls;
-
- if (service)
- {
- service->shutdown = NULL;
-
- destroy_service (service);
- }
-}
-
-static void
-callback_update_ego (void *cls,
- struct GNUNET_IDENTITY_Ego *ego,
- void **ctx,
- const char *identifier)
-{
- if ((!ego) || (!identifier))
- return;
-
- struct GNUNET_MESSENGER_Service *service = cls;
-
- update_service_ego(service, identifier, GNUNET_IDENTITY_ego_get_private_key(ego));
-}
-
-struct GNUNET_MESSENGER_Service*
-create_service (const struct GNUNET_CONFIGURATION_Handle *config, struct GNUNET_SERVICE_Handle *service_handle)
-{
- struct GNUNET_MESSENGER_Service *service = GNUNET_new(struct GNUNET_MESSENGER_Service);
-
- service->config = config;
- service->service = service_handle;
-
- service->shutdown = GNUNET_SCHEDULER_add_shutdown (&callback_shutdown_service, service);
-
- service->dir = NULL;
-
- if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_filename (service->config,
- GNUNET_MESSENGER_SERVICE_NAME,
- "MESSENGER_DIR", &(service->dir)))
- {
- if (service->dir)
- GNUNET_free(service->dir);
-
- service->dir = NULL;
- }
- else
- {
- if ((GNUNET_YES != GNUNET_DISK_directory_test (service->dir, GNUNET_YES)) && (GNUNET_OK
- != GNUNET_DISK_directory_create (service->dir)))
- {
- GNUNET_free(service->dir);
-
- service->dir = NULL;
- }
- }
-
- service->cadet = GNUNET_CADET_connect (service->config);
- service->identity = GNUNET_IDENTITY_connect (service->config, &callback_update_ego, service);
-
- service->egos = GNUNET_CONTAINER_multihashmap_create (8, GNUNET_NO);
-
- init_list_handles (&(service->handles));
-
- service->contacts = GNUNET_CONTAINER_multihashmap_create (8, GNUNET_NO);
- service->rooms = GNUNET_CONTAINER_multihashmap_create (8, GNUNET_NO);
-
- return service;
-}
-
-static int
-iterate_destroy_egos (void *cls, const struct GNUNET_HashCode *key, void *value)
-{
- struct GNUNET_MESSENGER_Ego *ego = value;
- GNUNET_free(ego);
- return GNUNET_YES;
-}
-
-static int
-iterate_destroy_rooms (void *cls, const struct GNUNET_HashCode *key, void *value)
-{
- struct GNUNET_MESSENGER_SrvRoom *room = value;
- destroy_room (room);
- return GNUNET_YES;
-}
-
-static int
-iterate_destroy_contacts (void *cls, const struct GNUNET_HashCode *key, void *value)
-{
- struct GNUNET_MESSENGER_SrvContact *contact = value;
- destroy_contact (contact);
- return GNUNET_YES;
-}
-
-void
-destroy_service (struct GNUNET_MESSENGER_Service *service)
-{
- if (service->shutdown)
- {
- GNUNET_SCHEDULER_cancel (service->shutdown);
-
- service->shutdown = NULL;
- }
-
- GNUNET_CONTAINER_multihashmap_iterate (service->egos, iterate_destroy_egos, NULL);
-
- clear_list_handles (&(service->handles));
-
- GNUNET_CONTAINER_multihashmap_iterate (service->rooms, iterate_destroy_rooms, NULL);
- GNUNET_CONTAINER_multihashmap_iterate (service->contacts, iterate_destroy_contacts, NULL);
-
- GNUNET_CONTAINER_multihashmap_destroy (service->egos);
- GNUNET_CONTAINER_multihashmap_destroy (service->rooms);
- GNUNET_CONTAINER_multihashmap_destroy (service->contacts);
-
- if (service->cadet)
- {
- GNUNET_CADET_disconnect (service->cadet);
-
- service->cadet = NULL;
- }
-
- if (service->identity)
- {
- GNUNET_IDENTITY_disconnect (service->identity);
-
- service->identity = NULL;
- }
-
- if (service->dir)
- {
- GNUNET_free(service->dir);
-
- service->dir = NULL;
- }
-
- GNUNET_SERVICE_shutdown (service->service);
-
- GNUNET_free(service);
-}
-
-struct GNUNET_MESSENGER_Ego*
-lookup_service_ego (struct GNUNET_MESSENGER_Service *service, const char *identifier)
-{
- GNUNET_assert(identifier);
-
- struct GNUNET_HashCode hash;
-
- GNUNET_CRYPTO_hash(identifier, strlen(identifier), &hash);
- return GNUNET_CONTAINER_multihashmap_get(service->egos, &hash);
-}
-
-void
-update_service_ego (struct GNUNET_MESSENGER_Service *service, const char *identifier,
- const struct GNUNET_IDENTITY_PrivateKey* key)
-{
- GNUNET_assert((identifier) && (key));
-
- struct GNUNET_HashCode hash;
-
- GNUNET_CRYPTO_hash(identifier, strlen(identifier), &hash);
-
- struct GNUNET_MESSENGER_Ego* ego = GNUNET_CONTAINER_multihashmap_get(service->egos, &hash);
-
- if (!ego)
- {
- ego = GNUNET_new(struct GNUNET_MESSENGER_Ego);
- GNUNET_CONTAINER_multihashmap_put(service->egos, &hash, ego, GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST);
- }
-
- GNUNET_memcpy(&(ego->priv), key, sizeof(*key));
-
- if (GNUNET_OK != GNUNET_IDENTITY_key_get_public(key, &(ego->pub)))
- GNUNET_log(GNUNET_ERROR_TYPE_WARNING, "Updating invalid ego key failed!\n");
-}
-
-struct GNUNET_MESSENGER_SrvHandle*
-add_service_handle (struct GNUNET_MESSENGER_Service *service, struct GNUNET_MQ_Handle *mq)
-{
- struct GNUNET_MESSENGER_SrvHandle *handle = create_handle (service, mq);
-
- if (handle)
- {
- add_list_handle (&(service->handles), handle);
- }
-
- return handle;
-}
-
-void
-remove_service_handle (struct GNUNET_MESSENGER_Service *service, struct GNUNET_MESSENGER_SrvHandle *handle)
-{
- if (!handle)
- return;
-
- if (GNUNET_YES == remove_list_handle (&(service->handles), handle))
- destroy_handle (handle);
-}
-
-int
-get_service_peer_identity (const struct GNUNET_MESSENGER_Service *service, struct GNUNET_PeerIdentity *peer)
-{
- return GNUNET_CRYPTO_get_peer_identity (service->config, peer);
-}
-
-struct GNUNET_MESSENGER_SrvContact*
-get_service_contact_by_pubkey (struct GNUNET_MESSENGER_Service *service, const struct GNUNET_IDENTITY_PublicKey *pubkey)
-{
- struct GNUNET_HashCode hash;
-
- GNUNET_CRYPTO_hash (pubkey, sizeof(*pubkey), &hash);
-
- struct GNUNET_MESSENGER_SrvContact *contact = GNUNET_CONTAINER_multihashmap_get (service->contacts, &hash);
-
- if (contact)
- return contact;
-
- contact = create_contact (pubkey);
-
- if (GNUNET_OK == GNUNET_CONTAINER_multihashmap_put (service->contacts, &hash, contact,
- GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST))
- return contact;
-
- destroy_contact (contact);
- return NULL;
-}
-
-void
-swap_service_contact_by_pubkey (struct GNUNET_MESSENGER_Service *service, struct GNUNET_MESSENGER_SrvContact *contact,
- const struct GNUNET_IDENTITY_PublicKey *pubkey)
-{
- const struct GNUNET_HashCode *hash = get_contact_id_from_key (contact);
-
- if (GNUNET_YES == GNUNET_CONTAINER_multihashmap_remove (service->contacts, hash, contact))
- {
- GNUNET_memcpy(&(contact->public_key), pubkey, sizeof(*pubkey));
-
- hash = get_contact_id_from_key (contact);
-
- GNUNET_CONTAINER_multihashmap_put (service->contacts, hash, contact,
- GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST);
- }
-}
-
-struct GNUNET_ShortHashCode*
-generate_service_new_member_id (struct GNUNET_MESSENGER_Service *service, const struct GNUNET_HashCode *key)
-{
- struct GNUNET_MESSENGER_SrvRoom *room = get_service_room (service, key);
-
- if (room)
- {
- return generate_room_member_id (room);
- }
- else
- {
- struct GNUNET_ShortHashCode *random_id = GNUNET_new(struct GNUNET_ShortHashCode);
- generate_free_member_id (random_id, NULL);
- return random_id;
- }
-}
-
-struct GNUNET_MESSENGER_SrvRoom*
-get_service_room (struct GNUNET_MESSENGER_Service *service, const struct GNUNET_HashCode *key)
-{
- return GNUNET_CONTAINER_multihashmap_get (service->rooms, key);
-}
-
-int
-open_service_room (struct GNUNET_MESSENGER_Service *service, struct GNUNET_MESSENGER_SrvHandle *handle,
- const struct GNUNET_HashCode *key)
-{
- struct GNUNET_MESSENGER_SrvRoom *room = get_service_room (service, key);
-
- if (room)
- return open_room (room, handle);
-
- room = create_room (handle, key);
-
- if ((GNUNET_YES == open_room (room, handle)) && (GNUNET_OK
- == GNUNET_CONTAINER_multihashmap_put (service->rooms, key, room, GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST)))
- return GNUNET_YES;
-
- destroy_room (room);
- return GNUNET_NO;
-}
-
-int
-entry_service_room (struct GNUNET_MESSENGER_Service *service, struct GNUNET_MESSENGER_SrvHandle *handle,
- const struct GNUNET_PeerIdentity *door, const struct GNUNET_HashCode *key)
-{
- struct GNUNET_MESSENGER_SrvRoom *room = get_service_room (service, key);
-
- if (room)
- {
- if (GNUNET_YES == entry_room_at (room, handle, door))
- return GNUNET_YES;
- else
- return GNUNET_NO;
- }
-
- room = create_room (handle, key);
-
- if ((GNUNET_YES == entry_room_at (room, handle, door)) && (GNUNET_OK
- == GNUNET_CONTAINER_multihashmap_put (service->rooms, key, room, GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST)))
- {
- return GNUNET_YES;
- }
- else
- {
- destroy_room (room);
- return GNUNET_NO;
- }
-
-}
-
-int
-close_service_room (struct GNUNET_MESSENGER_Service *service, struct GNUNET_MESSENGER_SrvHandle *handle,
- const struct GNUNET_HashCode *key)
-{
- struct GNUNET_MESSENGER_SrvRoom *room = get_service_room (service, key);
-
- if (!room)
- return GNUNET_NO;
-
- struct GNUNET_MESSENGER_Message *message = create_message_leave ();
-
- if (message)
- {
- struct GNUNET_HashCode hash;
-
- send_room_message (room, handle, message, &hash);
- destroy_message (message);
- }
-
- const struct GNUNET_ShortHashCode *id = get_handle_member_id (handle, key);
-
- GNUNET_assert(id);
-
- if (GNUNET_YES != GNUNET_CONTAINER_multihashmap_remove (handle->member_ids, key, id))
- return GNUNET_NO;
-
- struct GNUNET_MESSENGER_SrvHandle *member_handle = (struct GNUNET_MESSENGER_SrvHandle*) find_list_handle_by_member (
- &(service->handles), key);
-
- if (!member_handle)
- {
- if (GNUNET_OK == GNUNET_CONTAINER_multihashmap_remove (service->rooms, key, room))
- {
- destroy_room (room);
- return GNUNET_YES;
- }
- else
- return GNUNET_NO;
- }
-
- if (room->host == handle)
- room->host = member_handle;
-
- return GNUNET_YES;
-}
-
-static void
-get_room_data_subdir (struct GNUNET_MESSENGER_Service *service, struct GNUNET_MESSENGER_SrvRoom *room, char **dir)
-{
- GNUNET_asprintf (dir, "%s%s%c%s%c", service->dir, "rooms", DIR_SEPARATOR, GNUNET_h2s (&(room->key)), DIR_SEPARATOR);
-}
-
-void
-load_service_room_and_messages (struct GNUNET_MESSENGER_Service *service, struct GNUNET_MESSENGER_SrvRoom *room)
-{
- char *room_dir;
- get_room_data_subdir (service, room, &room_dir);
-
- if (GNUNET_YES == GNUNET_DISK_directory_test (room_dir, GNUNET_YES))
- {
- load_message_store (&room->store, room_dir);
-
- char *config_file;
- GNUNET_asprintf (&config_file, "%s%s", room_dir, "room.cfg");
-
- struct GNUNET_CONFIGURATION_Handle *cfg = GNUNET_CONFIGURATION_create ();
-
- if ((GNUNET_YES == GNUNET_DISK_file_test (config_file)) && (GNUNET_OK
- == GNUNET_CONFIGURATION_parse (cfg, config_file)))
- {
- unsigned long long access;
-
- if (GNUNET_OK == GNUNET_CONFIGURATION_get_value_number (cfg, "room", "access-rule", &access))
- room->strict_access = (int) (access);
-
- char *message_string;
-
- if ((GNUNET_OK == GNUNET_CONFIGURATION_get_value_string (cfg, "room", "last-message", &message_string)) && (message_string))
- {
- struct GNUNET_HashCode hash;
-
- GNUNET_CRYPTO_hash_from_string(message_string, &hash);
-
- const struct GNUNET_MESSENGER_Message *message = get_room_message (room, room->host, &hash, GNUNET_NO);
-
- if (message)
- update_room_last_messages (room, message, &hash);
-
- GNUNET_free(message_string);
- }
- }
-
- GNUNET_CONFIGURATION_destroy (cfg);
-
- GNUNET_free(config_file);
- }
-
- GNUNET_free(room_dir);
-}
-
-void
-save_service_room_and_messages (struct GNUNET_MESSENGER_Service *service, struct GNUNET_MESSENGER_SrvRoom *room)
-{
- if (GNUNET_YES != GNUNET_CONTAINER_multihashmap_contains (service->rooms, &(room->key)))
- {
- return;
- }
-
- char *room_dir;
- get_room_data_subdir (service, room, &room_dir);
-
- if ((GNUNET_YES == GNUNET_DISK_directory_test (room_dir, GNUNET_NO)) || (GNUNET_OK
- == GNUNET_DISK_directory_create (room_dir)))
- {
- save_message_store (&room->store, room_dir);
-
- char *config_file;
- GNUNET_asprintf (&config_file, "%s%s", room_dir, "room.cfg");
-
- struct GNUNET_CONFIGURATION_Handle *cfg = GNUNET_CONFIGURATION_create ();
-
- GNUNET_CONFIGURATION_set_value_number (cfg, "room", "access-rule", room->strict_access);
-
- if (room->last_messages.head)
- GNUNET_CONFIGURATION_set_value_string (cfg, "room", "last-message",
- GNUNET_h2s_full (&(room->last_messages.head->hash)));
-
- GNUNET_CONFIGURATION_write (cfg, config_file);
- GNUNET_CONFIGURATION_destroy (cfg);
-
- GNUNET_free(config_file);
- }
-
- GNUNET_free(room_dir);
-}
-
-void
-handle_service_message (struct GNUNET_MESSENGER_Service *service, struct GNUNET_MESSENGER_SrvRoom *room,
- const struct GNUNET_MESSENGER_Message *message, const struct GNUNET_HashCode *hash)
-{
- struct GNUNET_MESSENGER_ListHandle *element = service->handles.head;
-
- const uint16_t length = get_message_size (message);
-
- while (element)
- {
- struct GNUNET_MESSENGER_SrvHandle *handle = (struct GNUNET_MESSENGER_SrvHandle*) element->handle;
-
- if ((handle->mq) && (get_handle_member_id (handle, &(room->key))))
- {
- struct GNUNET_MESSENGER_RecvMessage *msg;
- struct GNUNET_MQ_Envelope *env;
-
- env = GNUNET_MQ_msg_extra(msg, length, GNUNET_MESSAGE_TYPE_MESSENGER_ROOM_RECV_MESSAGE);
-
- GNUNET_memcpy(&(msg->key), &(room->key), sizeof(room->key));
- GNUNET_memcpy(&(msg->hash), hash, sizeof(*hash));
-
- char *buffer = ((char*) msg) + sizeof(*msg);
- encode_message (message, length, buffer);
-
- GNUNET_MQ_send (handle->mq, env);
- }
-
- element = element->next;
- }
-}