From 1a7f68bbc042d1c527149a6c034f44573c42b68b Mon Sep 17 00:00:00 2001 From: Andrea Gianarda <andrea.gianarda@belledonne-communications.com> Date: Wed, 12 Feb 2025 11:59:51 +0100 Subject: [PATCH] Improve resiliance of SDK clients against server errors when searching a chat stored in the RAM: Ensure that linphone_core_search_chat_room_2 doesn't do a SIP address comparison as stated in the RFC. In fact, doing that leads to being too exposed to server instabilities. For example, if a server for whatever reason removes the conf-id parameter from the chatroom peer address, it will prevent to client to join any new chatroom as all will match the corrupted chat Add class ConferenceContext to easily compare two chatrooms or conference based on the parameters, local and remote address and the participants --- coreapi/chat.c | 27 ++-- coreapi/linphonecore.c | 7 +- src/CMakeLists.txt | 2 + src/chat/chat-room/abstract-chat-room.h | 8 ++ src/chat/chat-room/basic-chat-room.cpp | 8 ++ src/chat/chat-room/basic-chat-room.h | 1 + src/chat/chat-room/chat-room.cpp | 8 ++ src/chat/chat-room/chat-room.h | 1 + src/conference/conference-context.cpp | 100 ++++++++++++++ src/conference/conference-context.h | 69 ++++++++++ src/conference/conference.cpp | 8 ++ src/conference/conference.h | 1 + src/conference/session/call-session.cpp | 5 +- src/core/core-chat-room.cpp | 75 +++-------- src/core/core.cpp | 59 +++------ tester/audio_video_conference_tester.c | 107 ++++++++------- tester/db/chatroom_conference.db | Bin 221184 -> 221184 bytes tester/local-conference-tester-functions.cpp | 132 ++++++++++--------- tester/local-scheduled-conference-tester.cpp | 2 +- tester/main-db-tester.cpp | 27 +++- tester/tester.c | 5 +- 21 files changed, 415 insertions(+), 237 deletions(-) create mode 100644 src/conference/conference-context.cpp create mode 100644 src/conference/conference-context.h diff --git a/coreapi/chat.c b/coreapi/chat.c index 52efa947a9..9316e02fc4 100644 --- a/coreapi/chat.c +++ b/coreapi/chat.c @@ -149,11 +149,11 @@ LinphoneChatRoom *linphone_core_create_chat_room_7(LinphoneCore *lc, participantsList.push_back(LinphonePrivate::Address::toCpp(data)->getSharedFromThis()); } - shared_ptr<const LinphonePrivate::Address> identityAddress = + shared_ptr<const LinphonePrivate::Address> localAddress = localAddr ? LinphonePrivate::Address::toCpp(localAddr)->getSharedFromThis() : L_GET_PRIVATE_FROM_C_OBJECT(lc)->getDefaultLocalAddress(nullptr, false); shared_ptr<LinphonePrivate::AbstractChatRoom> room = - L_GET_PRIVATE_FROM_C_OBJECT(lc)->createChatRoom(conferenceParams, identityAddress, participantsList); + L_GET_PRIVATE_FROM_C_OBJECT(lc)->createChatRoom(conferenceParams, localAddress, participantsList); if (room) { auto cRoom = room->toC(); linphone_chat_room_ref(cRoom); @@ -181,13 +181,12 @@ LinphoneChatRoom *linphone_core_search_chat_room_2(const LinphoneCore *lc, params ? LinphonePrivate::ConferenceParams::toCpp(params)->clone()->toSharedPtr() : nullptr; const list<std::shared_ptr<LinphonePrivate::Address>> participantsList = LinphonePrivate::Address::getCppListFromCList(participants); - shared_ptr<const LinphonePrivate::Address> identityAddress = - localAddr ? LinphonePrivate::Address::toCpp(localAddr)->getSharedFromThis() - : L_GET_PRIVATE_FROM_C_OBJECT(lc)->getDefaultLocalAddress(nullptr, false); + shared_ptr<const LinphonePrivate::Address> localAddress = + localAddr ? LinphonePrivate::Address::toCpp(localAddr)->getSharedFromThis() : nullptr; shared_ptr<const LinphonePrivate::Address> remoteAddress = remoteAddr ? LinphonePrivate::Address::toCpp(remoteAddr)->getSharedFromThis() : nullptr; shared_ptr<LinphonePrivate::AbstractChatRoom> room = L_GET_PRIVATE_FROM_C_OBJECT(lc)->searchChatRoom( - conferenceParams, identityAddress, remoteAddress, participantsList); + conferenceParams, localAddress, remoteAddress, participantsList); if (room) return room->toC(); return NULL; } @@ -207,15 +206,15 @@ void linphone_core_delete_chat_room(LinphoneCore *lc, LinphoneChatRoom *cr) { LinphonePrivate::AbstractChatRoom::toCpp(cr)->deleteFromDb(); } -// Deprecated see linphone_core_search_chat_room +// Deprecated see linphone_core_search_chat_room_2 LinphoneChatRoom *linphone_core_get_chat_room(LinphoneCore *lc, const LinphoneAddress *peerAddr) { return linphone_core_get_chat_room_2(lc, peerAddr, NULL); } -// Deprecated see linphone_core_search_chat_room +// Deprecated see linphone_core_search_chat_room_2 LinphoneChatRoom * linphone_core_get_chat_room_2(LinphoneCore *lc, const LinphoneAddress *peer_addr, const LinphoneAddress *local_addr) { - LinphoneChatRoom *result = linphone_core_search_chat_room(lc, NULL, local_addr, peer_addr, NULL); + LinphoneChatRoom *result = linphone_core_search_chat_room_2(lc, NULL, local_addr, peer_addr, NULL); if (result == NULL) { bctbx_list_t *paricipants = bctbx_list_prepend(NULL, (LinphoneAddress *)peer_addr); LinphoneChatRoomParams *params = linphone_core_create_default_chat_room_params(lc); @@ -229,7 +228,7 @@ linphone_core_get_chat_room_2(LinphoneCore *lc, const LinphoneAddress *peer_addr return result; } -// Deprecated see linphone_core_search_chat_room +// Deprecated see linphone_core_search_chat_room_2 LinphoneChatRoom *linphone_core_get_chat_room_from_uri(LinphoneCore *lc, const char *to) { LinphoneAddress *addr = linphone_core_interpret_url(lc, to); LinphoneChatRoom *room = linphone_core_get_chat_room(lc, addr); @@ -237,15 +236,15 @@ LinphoneChatRoom *linphone_core_get_chat_room_from_uri(LinphoneCore *lc, const c return room; } -// Deprecated see linphone_core_search_chat_room +// Deprecated see linphone_core_search_chat_room_2 LinphoneChatRoom *linphone_core_find_chat_room(const LinphoneCore *lc, const LinphoneAddress *peer_addr, const LinphoneAddress *local_addr) { - LinphoneChatRoom *result = linphone_core_search_chat_room(lc, NULL, local_addr, peer_addr, NULL); + LinphoneChatRoom *result = linphone_core_search_chat_room_2(lc, NULL, local_addr, peer_addr, NULL); return result; } -// Deprecated see linphone_core_search_chat_room +// Deprecated see linphone_core_search_chat_room_2 LinphoneChatRoom *linphone_core_find_one_to_one_chat_room(const LinphoneCore *lc, const LinphoneAddress *local_addr, const LinphoneAddress *participant_addr) { @@ -263,7 +262,7 @@ LinphoneChatRoom *linphone_core_find_one_to_one_chat_room(const LinphoneCore *lc return result; } -// Deprecated see linphone_core_search_chat_room +// Deprecated see linphone_core_search_chat_room_2 LinphoneChatRoom *linphone_core_find_one_to_one_chat_room_2(const LinphoneCore *lc, const LinphoneAddress *local_addr, const LinphoneAddress *participant_addr, diff --git a/coreapi/linphonecore.c b/coreapi/linphonecore.c index 078e4f3040..7193353bfd 100644 --- a/coreapi/linphonecore.c +++ b/coreapi/linphonecore.c @@ -9494,13 +9494,12 @@ LinphoneConference *linphone_core_search_conference(const LinphoneCore *lc, LinphonePrivate::Utils::bctbxListToCppSharedPtrList<LinphoneAddress, LinphonePrivate::Address>( participants); } - shared_ptr<const LinphonePrivate::Address> identityAddress = - localAddr ? LinphonePrivate::Address::getSharedFromThis(localAddr) - : L_GET_PRIVATE_FROM_C_OBJECT(lc)->getDefaultLocalAddress(nullptr, false); + shared_ptr<const LinphonePrivate::Address> localAddress = + localAddr ? LinphonePrivate::Address::getSharedFromThis(localAddr) : nullptr; shared_ptr<const LinphonePrivate::Address> remoteAddress = remoteAddr ? LinphonePrivate::Address::toCpp(remoteAddr)->getSharedFromThis() : nullptr; shared_ptr<LinphonePrivate::Conference> conf = L_GET_CPP_PTR_FROM_C_OBJECT(lc)->searchConference( - conferenceParams, identityAddress, remoteAddress, participantsList); + conferenceParams, localAddress, remoteAddress, participantsList); LinphoneConference *c_conference = NULL; if (conf) { c_conference = conf->toC(); diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index cc7867b4d5..c5baadd5a0 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -183,6 +183,7 @@ set(LINPHONE_CXX_OBJECTS_PRIVATE_HEADER_FILES conference/conference-listener.h conference/notify-conference-listener.h conference/conference.h + conference/conference-context.h conference/server-conference.h conference/params/call-session-params-p.h conference/params/call-session-params.h @@ -498,6 +499,7 @@ set(LINPHONE_CXX_OBJECTS_SOURCE_FILES conference/conference-info.cpp conference/conference-scheduler.cpp conference/conference.cpp + conference/conference-context.cpp conference/conference-interface.cpp conference/sip-conference-scheduler.cpp conference/ccmp-conference-scheduler.cpp diff --git a/src/chat/chat-room/abstract-chat-room.h b/src/chat/chat-room/abstract-chat-room.h index 3f93072019..13d727c920 100644 --- a/src/chat/chat-room/abstract-chat-room.h +++ b/src/chat/chat-room/abstract-chat-room.h @@ -203,6 +203,7 @@ public: virtual std::shared_ptr<Address> getConferenceAddress() const = 0; virtual std::shared_ptr<Participant> findParticipant(const std::shared_ptr<Address> &address) const = 0; virtual std::list<std::shared_ptr<Participant>> getParticipants() const = 0; + virtual std::list<std::shared_ptr<Address>> getParticipantAddresses() const = 0; virtual bool canHandleParticipants() const = 0; virtual std::shared_ptr<Conference> getConference() const = 0; @@ -283,6 +284,13 @@ std::ostream &operator<<(std::ostream &lhs, AbstractChatRoom::SecurityLevel e); std::ostream &operator<<(std::ostream &lhs, AbstractChatRoom::EphemeralMode e); +inline std::ostream &operator<<(std::ostream &str, const AbstractChatRoom &chatRoom) { + const auto &conferenceAddress = chatRoom.getConferenceAddress(); + str << "Conference [" << &chatRoom << "] (" + << (conferenceAddress ? conferenceAddress->toString() : std::string("sip:")) << ")"; + return str; +} + LINPHONE_END_NAMESPACE #endif // ifndef _L_ABSTRACT_CHAT_ROOM_H_ diff --git a/src/chat/chat-room/basic-chat-room.cpp b/src/chat/chat-room/basic-chat-room.cpp index 1b5a82c3df..9fd577a257 100644 --- a/src/chat/chat-room/basic-chat-room.cpp +++ b/src/chat/chat-room/basic-chat-room.cpp @@ -147,4 +147,12 @@ std::list<std::shared_ptr<Participant>> BasicChatRoom::getParticipants() const { return mParticipants; } +std::list<std::shared_ptr<Address>> BasicChatRoom::getParticipantAddresses() const { + list<std::shared_ptr<Address>> addresses; + for (auto &participant : mParticipants) { + addresses.push_back(participant->getAddress()); + } + return addresses; +} + LINPHONE_END_NAMESPACE diff --git a/src/chat/chat-room/basic-chat-room.h b/src/chat/chat-room/basic-chat-room.h index 321134efa8..662b0db585 100644 --- a/src/chat/chat-room/basic-chat-room.h +++ b/src/chat/chat-room/basic-chat-room.h @@ -57,6 +57,7 @@ public: bool isMe(const std::shared_ptr<Address> &address) const override; std::shared_ptr<Participant> getMe() const override; std::list<std::shared_ptr<Participant>> getParticipants() const override; + std::list<std::shared_ptr<Address>> getParticipantAddresses() const override; protected: explicit BasicChatRoom(const std::shared_ptr<Core> &core, diff --git a/src/chat/chat-room/chat-room.cpp b/src/chat/chat-room/chat-room.cpp index 17a50ca9cc..0cecf38bf1 100644 --- a/src/chat/chat-room/chat-room.cpp +++ b/src/chat/chat-room/chat-room.cpp @@ -1036,6 +1036,14 @@ std::list<std::shared_ptr<Participant>> ChatRoom::getParticipants() const { return conference->getParticipants(); } +std::list<std::shared_ptr<Address>> ChatRoom::getParticipantAddresses() const { + const auto conference = getConference(); + if (!conference) { + return std::list<std::shared_ptr<Address>>(); + } + return conference->getParticipantAddresses(); +} + std::shared_ptr<ConferenceParams> ChatRoom::getCurrentParams() const { const auto conference = getConference(); if (!conference) { diff --git a/src/chat/chat-room/chat-room.h b/src/chat/chat-room/chat-room.h index e02c86c989..2b5a8bae0b 100644 --- a/src/chat/chat-room/chat-room.h +++ b/src/chat/chat-room/chat-room.h @@ -136,6 +136,7 @@ public: std::shared_ptr<Address> getConferenceAddress() const override; std::shared_ptr<Participant> findParticipant(const std::shared_ptr<Address> &address) const override; std::list<std::shared_ptr<Participant>> getParticipants() const override; + std::list<std::shared_ptr<Address>> getParticipantAddresses() const override; virtual std::shared_ptr<Conference> getConference() const override; diff --git a/src/conference/conference-context.cpp b/src/conference/conference-context.cpp new file mode 100644 index 0000000000..435eff0dd7 --- /dev/null +++ b/src/conference/conference-context.cpp @@ -0,0 +1,100 @@ +/* + * Copyright (c) 2010-2022 Belledonne Communications SARL. + * + * This file is part of Liblinphone + * (see https://gitlab.linphone.org/BC/public/liblinphone). + * + * This program 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. + * + * This program 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/>. + */ + +#include "conference/conference-context.h" + +#include "conference/conference-id.h" +#include "conference/conference-params.h" + +LINPHONE_BEGIN_NAMESPACE + +ConferenceContext::ConferenceContext(const std::shared_ptr<ConferenceParams> ¶ms, + const std::shared_ptr<const Address> &localAddress, + const std::shared_ptr<const Address> &remoteAddress, + const std::list<std::shared_ptr<Address>> &participants) { + mParams = params; + mParticipants = participants; + mLocalAddress = (localAddress) ? localAddress->getUriWithoutGruu() : Address(); + mRemoteAddress = (remoteAddress) ? remoteAddress->getUriWithoutGruu() : Address(); +} + +bool ConferenceContext::operator==(const ConferenceContext &other) const { + if (mLocalAddress.isValid() && + (mLocalAddress.toStringUriOnlyOrdered(false) != other.getLocalAddress().toStringUriOnlyOrdered(false))) + return false; + if (mRemoteAddress.isValid() && + (mRemoteAddress.toStringUriOnlyOrdered(false) != other.getRemoteAddress().toStringUriOnlyOrdered(false))) + return false; + + // Check parameters only if pointer provided as argument is not null + if (mParams) { + const auto &otherParams = other.getParams(); + if (mParams->audioEnabled() != otherParams->audioEnabled()) return false; + if (mParams->videoEnabled() != otherParams->videoEnabled()) return false; + if (mParams->chatEnabled() != otherParams->chatEnabled()) return false; + if (mParams->getSecurityLevel() != otherParams->getSecurityLevel()) return false; + + if (mParams->audioEnabled() || mParams->videoEnabled()) { + if (!mParams->getUtf8Subject().empty() && + (mParams->getUtf8Subject().compare(otherParams->getUtf8Subject()) != 0)) + return false; + if (mParams->localParticipantEnabled() != otherParams->localParticipantEnabled()) return false; + } + + if (mParams->chatEnabled()) { + if (mParams->getChatParams()->getBackend() != otherParams->getChatParams()->getBackend()) return false; + + if (mParams->isGroup() != otherParams->isGroup()) return false; + + if (mParams->isGroup() && + (otherParams->getChatParams()->getBackend() == LinphonePrivate::ChatParams::Backend::Basic)) + return false; + + if (mParams->getChatParams()->isEncrypted() != otherParams->getChatParams()->isEncrypted()) return false; + + // Subject doesn't make any sense for basic chat room + if ((mParams->getChatParams()->getBackend() == LinphonePrivate::ChatParams::Backend::FlexisipChat) && + (!mParams->getUtf8Subject().empty() && mParams->getUtf8Subject() != otherParams->getUtf8Subject())) + return false; + } + } + + // Check participants only if list provided as argument is not empty + if (mParticipants.empty() == false) { + const auto &otherParticipants = other.getParticipants(); + if (mParticipants.size() != otherParticipants.size()) return false; + for (const auto &participant : mParticipants) { + bool found = false; + for (const auto &otherParticipant : otherParticipants) { + if (participant->weakEqual(*otherParticipant)) { + found = true; + break; + } + } + if (!found) { + return false; + } + } + } + + return true; +} + +LINPHONE_END_NAMESPACE diff --git a/src/conference/conference-context.h b/src/conference/conference-context.h new file mode 100644 index 0000000000..72fa3825a6 --- /dev/null +++ b/src/conference/conference-context.h @@ -0,0 +1,69 @@ +/* + * Copyright (c) 2010-2022 Belledonne Communications SARL. + * + * This file is part of Liblinphone + * (see https://gitlab.linphone.org/BC/public/liblinphone). + * + * This program 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. + * + * This program 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/>. + */ + +#ifndef _L_CONFERENCE_CONTEXT_H_ +#define _L_CONFERENCE_CONTEXT_H_ + +#include <list> +#include <memory> + +#include "address/address.h" +#include "linphone/utils/general.h" + +LINPHONE_BEGIN_NAMESPACE + +class ConferenceParams; + +class ConferenceContext { +public: + ConferenceContext() = delete; + ConferenceContext(const std::shared_ptr<ConferenceParams> ¶ms, + const std::shared_ptr<const Address> &localAddress, + const std::shared_ptr<const Address> &remoteAddress, + const std::list<std::shared_ptr<Address>> &participants); + ConferenceContext(ConferenceContext &&other) = delete; + ConferenceContext(const ConferenceContext &other) = delete; + virtual ~ConferenceContext() = default; + + inline const std::shared_ptr<const ConferenceParams> getParams() const { + return mParams; + } + inline const std::list<std::shared_ptr<Address>> &getParticipants() const { + return mParticipants; + } + inline const Address &getLocalAddress() const { + return mLocalAddress; + } + inline const Address &getRemoteAddress() const { + return mRemoteAddress; + } + + bool operator==(const ConferenceContext &other) const; + +private: + std::shared_ptr<const ConferenceParams> mParams; + std::list<std::shared_ptr<Address>> mParticipants; + Address mLocalAddress; + Address mRemoteAddress; +}; + +LINPHONE_END_NAMESPACE + +#endif // ifndef _L_CONFERENCE_CONTEXT_H_ diff --git a/src/conference/conference.cpp b/src/conference/conference.cpp index 678f9bb487..ab3faf158c 100644 --- a/src/conference/conference.cpp +++ b/src/conference/conference.cpp @@ -735,6 +735,14 @@ const list<shared_ptr<Participant>> &Conference::getParticipants() const { return mParticipants; } +std::list<std::shared_ptr<Address>> Conference::getParticipantAddresses() const { + list<std::shared_ptr<Address>> addresses; + for (auto &participant : mParticipants) { + addresses.push_back(participant->getAddress()); + } + return addresses; +} + list<shared_ptr<ParticipantDevice>> Conference::getParticipantDevices(bool includeMe) const { list<shared_ptr<ParticipantDevice>> devices; for (const auto &p : mParticipants) { diff --git a/src/conference/conference.h b/src/conference/conference.h index 0c6fe5a553..fcb466b442 100644 --- a/src/conference/conference.h +++ b/src/conference/conference.h @@ -122,6 +122,7 @@ public: int getParticipantCount() const override; const std::list<std::shared_ptr<Participant>> &getParticipants() const override; + std::list<std::shared_ptr<Address>> getParticipantAddresses() const; std::list<std::shared_ptr<ParticipantDevice>> getParticipantDevices(bool includeMe = true) const override; std::shared_ptr<Participant> getScreenSharingParticipant() const; std::shared_ptr<ParticipantDevice> getScreenSharingDevice() const; diff --git a/src/conference/session/call-session.cpp b/src/conference/session/call-session.cpp index 54b080aaf2..301517a2ca 100644 --- a/src/conference/session/call-session.cpp +++ b/src/conference/session/call-session.cpp @@ -133,9 +133,8 @@ void CallSessionPrivate::setState(CallSession::State newState, const string &mes ref->addListener(conference); } } else if (op->getRemoteContactAddress()) { - std::shared_ptr<Address> remoteContactAddress = Address::create(); - remoteContactAddress->setImpl(op->getRemoteContactAddress()); - if (remoteContactAddress->hasParam(Conference::IsFocusParameter)) { + if (sal_address_has_param(op->getRemoteContactAddress(), + Conference::IsFocusParameter.c_str())) { const auto &conferenceInfo = Utils::createConferenceInfoFromOp(op, true); if (conferenceInfo->getUri()->isValid()) { #ifdef HAVE_DB_STORAGE diff --git a/src/core/core-chat-room.cpp b/src/core/core-chat-room.cpp index 3909bae59b..d3ee6e328e 100644 --- a/src/core/core-chat-room.cpp +++ b/src/core/core-chat-room.cpp @@ -30,6 +30,7 @@ #include "chat/chat-room/abstract-chat-room.h" #include "chat/chat-room/basic-chat-room.h" #include "chat/chat-room/chat-room.h" +#include "conference/conference-context.h" #include "conference/participant-info.h" #include "conference/participant.h" #include "conference/server-conference.h" @@ -271,69 +272,25 @@ shared_ptr<AbstractChatRoom> CorePrivate::createBasicChatRoom(const ConferenceId return chatRoom; } -shared_ptr<AbstractChatRoom> -CorePrivate::searchChatRoom(const shared_ptr<ConferenceParams> ¶ms, +std::shared_ptr<AbstractChatRoom> +CorePrivate::searchChatRoom(const std::shared_ptr<ConferenceParams> ¶ms, const std::shared_ptr<const Address> &localAddress, const std::shared_ptr<const Address> &remoteAddress, const std::list<std::shared_ptr<Address>> &participants) const { L_Q(); - for (const auto &chatRoom : q->getRawChatRoomList()) { - if (params) { - const auto &chatRoomParams = chatRoom->getCurrentParams(); - - if (params->audioEnabled() != chatRoomParams->audioEnabled()) continue; - if (params->videoEnabled() != chatRoomParams->videoEnabled()) continue; - - if (params->getChatParams()->getBackend() != chatRoomParams->getChatParams()->getBackend()) continue; - - if (params->isGroup() != chatRoomParams->isGroup()) continue; - - if (params->isGroup() && - (chatRoomParams->getChatParams()->getBackend() == LinphonePrivate::ChatParams::Backend::Basic)) - continue; - - if (params->getChatParams()->isEncrypted() != chatRoomParams->getChatParams()->isEncrypted()) continue; - - // Subject doesn't make any sense for basic chat room - if ((params->getChatParams()->getBackend() == LinphonePrivate::ChatParams::Backend::FlexisipChat) && - (!params->getUtf8Subject().empty() && params->getUtf8Subject() != chatRoom->getSubjectUtf8())) - continue; - } - - std::shared_ptr<Address> curLocalAddress = chatRoom->getLocalAddress(); - const auto curLocalAddressWithoutGruu = curLocalAddress->getUriWithoutGruu(); - const auto localAddressWithoutGruu = - (localAddress && localAddress->isValid()) ? localAddress->getUriWithoutGruu() : Address(); - if (localAddressWithoutGruu.isValid() && (localAddressWithoutGruu != curLocalAddressWithoutGruu)) continue; - - std::shared_ptr<Address> curRemoteAddress = chatRoom->getPeerAddress(); - const auto curRemoteAddressWithoutGruu = curRemoteAddress->getUriWithoutGruu(); - const auto remoteAddressWithoutGruu = - (remoteAddress && remoteAddress->isValid()) ? remoteAddress->getUriWithoutGruu() : Address(); - if (remoteAddressWithoutGruu.isValid() && (remoteAddressWithoutGruu != curRemoteAddressWithoutGruu)) continue; - - const auto &chatRoomParticipants = chatRoom->getParticipants(); - const auto expectedParticipantNb = participants.size(); - if ((expectedParticipantNb > 0) && (chatRoomParticipants.size() != expectedParticipantNb)) continue; - bool allFound = true; - for (const auto &participant : participants) { - bool found = false; - for (const auto &p : chatRoomParticipants) { - if (participant->weakEqual(*(p->getAddress()))) { - found = true; - break; - } - } - if (!found) { - allFound = false; - break; - } - } - if (!allFound) continue; - - return chatRoom; + ConferenceContext referenceConferenceContext(params, localAddress, remoteAddress, participants); + const auto &chatRooms = q->getRawChatRoomList(); + const auto it = std::find_if(chatRooms.begin(), chatRooms.end(), [&](const auto &chatRoom) { + ConferenceContext conferenceContext(chatRoom->getCurrentParams(), chatRoom->getLocalAddress(), + chatRoom->getPeerAddress(), chatRoom->getParticipantAddresses()); + return (referenceConferenceContext == conferenceContext); + }); + + std::shared_ptr<AbstractChatRoom> chatRoom; + if (it != chatRooms.cend()) { + chatRoom = *it; } - return nullptr; + return chatRoom; } shared_ptr<AbstractChatRoom> @@ -374,7 +331,7 @@ CorePrivate::createChatRoom(const shared_ptr<ConferenceParams> ¶ms, chatRoom = q->findOneToOneChatRoom(localAddr, participants.front(), false, true, params->getChatParams()->isEncrypted()); if (chatRoom != nullptr) { - lWarning() << "Found already existing 1-1 chat room that matches, using this one " << chatRoom; + lWarning() << "Found already existing 1-1 chat room that matches, using this one " << *chatRoom; return chatRoom; } } diff --git a/src/core/core.cpp b/src/core/core.cpp index dd09d3fbc9..ac96c472a9 100644 --- a/src/core/core.cpp +++ b/src/core/core.cpp @@ -54,6 +54,7 @@ #include "chat/encryption/lime-x3dh-encryption-engine.h" #endif // HAVE_LIME_X3DH #include "chat/encryption/lime-x3dh-server-engine.h" +#include "conference/conference-context.h" #include "conference/conference-id-params.h" #include "conference/conference.h" #include "conference/handlers/client-conference-list-event-handler.h" @@ -1975,49 +1976,23 @@ void Core::deleteConference(const shared_ptr<const Conference> &conference) { deleteConference(conferenceId); } -shared_ptr<Conference> Core::searchConference(const shared_ptr<ConferenceParams> ¶ms, - const std::shared_ptr<const Address> &localAddress, - const std::shared_ptr<const Address> &remoteAddress, - const std::list<std::shared_ptr<Address>> &participants) const { +std::shared_ptr<Conference> Core::searchConference(const std::shared_ptr<ConferenceParams> ¶ms, + const std::shared_ptr<const Address> &localAddress, + const std::shared_ptr<const Address> &remoteAddress, + const std::list<std::shared_ptr<Address>> &participants) const { L_D(); - auto localAddressUri = (localAddress) ? localAddress->getUriWithoutGruu() : Address(); - auto remoteAddressUri = (remoteAddress) ? remoteAddress->getUriWithoutGruu() : Address(); - const auto it = std::find_if(d->mConferenceById.begin(), d->mConferenceById.end(), [&](const auto &p) { - // p is of type std::pair<ConferenceId, std::shared_ptr<Conference> - const auto &conference = p.second; - const ConferenceId &conferenceId = conference->getConferenceId(); - auto curLocalAddress = - (conferenceId.getLocalAddress()) ? conferenceId.getLocalAddress()->getUriWithoutGruu() : Address(); - if (localAddressUri.isValid() && (localAddressUri != curLocalAddress)) return false; - - auto curPeerAddress = - (conferenceId.getPeerAddress()) ? conferenceId.getPeerAddress()->getUriWithoutGruu() : Address(); - if (remoteAddressUri.isValid() && (remoteAddressUri != curPeerAddress)) return false; - - // Check parameters only if pointer provided as argument is not null - if (params) { - const auto &conferenceParams = conference->getCurrentParams(); - if (!params->getUtf8Subject().empty() && - (params->getUtf8Subject().compare(conferenceParams->getUtf8Subject()) != 0)) - return false; - if (params->chatEnabled() != conferenceParams->chatEnabled()) return false; - if (params->audioEnabled() != conferenceParams->audioEnabled()) return false; - if (params->videoEnabled() != conferenceParams->videoEnabled()) return false; - if (params->localParticipantEnabled() != conferenceParams->localParticipantEnabled()) return false; - } - - // Check participants only if list provided as argument is not empty - bool participantListMatch = true; - if (participants.empty() == false) { - const std::list<std::shared_ptr<Participant>> &confParticipants = conference->getParticipants(); - participantListMatch = - equal(participants.cbegin(), participants.cend(), confParticipants.cbegin(), confParticipants.cend(), - [](const auto &p1, const auto &p2) { return (p1->weakEqual(*p2->getAddress())); }); - } - return participantListMatch; - }); - - shared_ptr<Conference> conference = nullptr; + ConferenceContext referenceConferenceContext(params, localAddress, remoteAddress, participants); + const auto it = std::find_if( + d->mConferenceById.begin(), d->mConferenceById.end(), [&referenceConferenceContext](const auto &p) { + // p is of type std::pair<ConferenceId, std::shared_ptr<Conference> + const auto &conference = p.second; + const ConferenceId &conferenceId = conference->getConferenceId(); + ConferenceContext conferenceContext(conference->getCurrentParams(), conferenceId.getLocalAddress(), + conferenceId.getPeerAddress(), conference->getParticipantAddresses()); + return (referenceConferenceContext == conferenceContext); + }); + + std::shared_ptr<Conference> conference; if (it != d->mConferenceById.cend()) { conference = it->second; } diff --git a/tester/audio_video_conference_tester.c b/tester/audio_video_conference_tester.c index a1b2a20040..55abb9f189 100644 --- a/tester/audio_video_conference_tester.c +++ b/tester/audio_video_conference_tester.c @@ -1736,11 +1736,12 @@ static void simple_conference_with_participant_addition_from_non_admin(void) { for (bctbx_list_t *it = lcs; it; it = bctbx_list_next(it)) { LinphoneCore *c = (LinphoneCore *)bctbx_list_get_data(it); - LinphoneAddress *m_uri = linphone_address_new(linphone_core_get_identity(c)); + LinphoneAddress *m_uri = (linphone_core_conference_server_enabled(c)) + ? linphone_address_clone(marie_conference_address) + : linphone_address_new(linphone_core_get_identity(c)); LinphoneConference *m_conference = linphone_core_search_conference(c, NULL, m_uri, marie_conference_address, NULL); linphone_address_unref(m_uri); - BC_ASSERT_PTR_NOT_NULL(m_conference); if (m_conference) { BC_ASSERT_EQUAL(linphone_conference_get_participant_count(m_conference), @@ -2137,12 +2138,13 @@ static void simple_conference_with_one_participant_base(bool_t local) { const LinphoneAddress *marie_conference_address = linphone_conference_get_conference_address(conf); for (bctbx_list_t *it = all_manangers_in_conf; it; it = bctbx_list_next(it)) { LinphoneCoreManager *m = (LinphoneCoreManager *)bctbx_list_get_data(it); - - LinphoneAddress *uri = linphone_address_new(linphone_core_get_identity(m->lc)); + LinphoneAddress *m_uri = (linphone_core_conference_server_enabled(m->lc)) + ? linphone_address_clone(marie_conference_address) + : linphone_address_new(linphone_core_get_identity(m->lc)); LinphoneConference *conference = - linphone_core_search_conference(m->lc, NULL, uri, marie_conference_address, NULL); + linphone_core_search_conference(m->lc, NULL, m_uri, marie_conference_address, NULL); BC_ASSERT_PTR_NOT_NULL(conference); - linphone_address_unref(uri); + linphone_address_unref(m_uri); if (conference) { int no_parts = (local || (m == marie)) ? 3 : 2; BC_ASSERT_EQUAL(linphone_conference_get_participant_count(conference), no_parts, int, "%d"); @@ -2170,11 +2172,13 @@ static void simple_conference_with_one_participant_base(bool_t local) { BC_ASSERT_TRUE(wait_for_list(lcs, &m->stat.number_of_participants_removed, 1, 3000)); BC_ASSERT_TRUE(wait_for_list(lcs, &m->stat.number_of_participant_devices_removed, 1, 3000)); - LinphoneAddress *uri = linphone_address_new(linphone_core_get_identity(m->lc)); + LinphoneAddress *m_uri = (linphone_core_conference_server_enabled(m->lc)) + ? linphone_address_clone(marie_conference_address) + : linphone_address_new(linphone_core_get_identity(m->lc)); LinphoneConference *conference = - linphone_core_search_conference(m->lc, NULL, uri, marie_conference_address, NULL); + linphone_core_search_conference(m->lc, NULL, m_uri, marie_conference_address, NULL); BC_ASSERT_PTR_NOT_NULL(conference); - linphone_address_unref(uri); + linphone_address_unref(m_uri); if (conference) { BC_ASSERT_EQUAL(linphone_conference_get_participant_count(conference), no_parts, int, "%d"); } @@ -2196,11 +2200,13 @@ static void simple_conference_with_one_participant_base(bool_t local) { BC_ASSERT_TRUE(wait_for_list(lcs, &m->stat.number_of_participants_removed, 2, 3000)); BC_ASSERT_TRUE(wait_for_list(lcs, &m->stat.number_of_participant_devices_removed, 2, 3000)); int no_parts = (local || (m == marie)) ? 1 : 0; - LinphoneAddress *uri = linphone_address_new(linphone_core_get_identity(m->lc)); + LinphoneAddress *m_uri = (linphone_core_conference_server_enabled(m->lc)) + ? linphone_address_clone(marie_conference_address) + : linphone_address_new(linphone_core_get_identity(m->lc)); LinphoneConference *conference = - linphone_core_search_conference(m->lc, NULL, uri, marie_conference_address, NULL); + linphone_core_search_conference(m->lc, NULL, m_uri, marie_conference_address, NULL); BC_ASSERT_PTR_NOT_NULL(conference); - linphone_address_unref(uri); + linphone_address_unref(m_uri); if (conference) { BC_ASSERT_EQUAL(linphone_conference_get_participant_count(conference), no_parts, int, "%d"); } @@ -2359,11 +2365,9 @@ static void simple_conference_with_user_defined_layout(const LinphoneConferenceL all_manangers_in_conf = bctbx_list_append(all_manangers_in_conf, marie); const LinphoneAddress *marie_conference_address = linphone_conference_get_conference_address(conf); - LinphoneAddress *focus_identity = linphone_address_new(linphone_core_get_identity(focus_mgr->lc)); LinphoneConference *focus_conference = - linphone_core_search_conference(focus_mgr->lc, NULL, focus_identity, marie_conference_address, NULL); + linphone_core_search_conference(focus_mgr->lc, NULL, marie_conference_address, marie_conference_address, NULL); BC_ASSERT_PTR_NOT_NULL(focus_conference); - linphone_address_unref(focus_identity); for (bctbx_list_t *it = all_manangers_in_conf; it; it = bctbx_list_next(it)) { LinphoneCoreManager *m = (LinphoneCoreManager *)bctbx_list_get_data(it); @@ -2501,11 +2505,9 @@ static void simple_conference_with_user_defined_layout(const LinphoneConferenceL BC_ASSERT_EQUAL(new_layout, remote_conf_layout, int, "%d"); } - LinphoneAddress *furi = linphone_address_new(linphone_core_get_identity(focus_mgr->lc)); - LinphoneConference *fconf = - linphone_core_search_conference(focus_mgr->lc, NULL, furi, local_conference_address, NULL); + LinphoneConference *fconf = linphone_core_search_conference(focus_mgr->lc, NULL, local_conference_address, + local_conference_address, NULL); BC_ASSERT_PTR_NOT_NULL(fconf); - linphone_address_unref(furi); if (fconf) { LinphoneParticipant *participant = linphone_conference_find_participant(fconf, michelle->identity); BC_ASSERT_PTR_NOT_NULL(participant); @@ -2916,11 +2918,13 @@ static void simple_conference_with_one_participant(void) { for (bctbx_list_t *it = all_manangers_in_conf; it; it = bctbx_list_next(it)) { LinphoneCoreManager *m = (LinphoneCoreManager *)bctbx_list_get_data(it); - LinphoneAddress *uri = linphone_address_new(linphone_core_get_identity(m->lc)); + LinphoneAddress *m_uri = (linphone_core_conference_server_enabled(m->lc)) + ? linphone_address_clone(marie_conference_address) + : linphone_address_new(linphone_core_get_identity(m->lc)); LinphoneConference *conference = - linphone_core_search_conference(m->lc, NULL, uri, marie_conference_address, NULL); + linphone_core_search_conference(m->lc, NULL, m_uri, marie_conference_address, NULL); BC_ASSERT_PTR_NOT_NULL(conference); - linphone_address_unref(uri); + linphone_address_unref(m_uri); if (conference) { BC_ASSERT_EQUAL(linphone_conference_get_participant_count(conference), 3, int, "%d"); } @@ -2943,11 +2947,13 @@ static void simple_conference_with_one_participant(void) { for (bctbx_list_t *it = all_manangers_in_conf; it; it = bctbx_list_next(it)) { LinphoneCoreManager *m = (LinphoneCoreManager *)bctbx_list_get_data(it); - LinphoneAddress *uri = linphone_address_new(linphone_core_get_identity(m->lc)); + LinphoneAddress *m_uri = (linphone_core_conference_server_enabled(m->lc)) + ? linphone_address_clone(marie_conference_address) + : linphone_address_new(linphone_core_get_identity(m->lc)); LinphoneConference *conference = - linphone_core_search_conference(m->lc, NULL, uri, marie_conference_address, NULL); + linphone_core_search_conference(m->lc, NULL, m_uri, marie_conference_address, NULL); BC_ASSERT_PTR_NOT_NULL(conference); - linphone_address_unref(uri); + linphone_address_unref(m_uri); if (conference) { BC_ASSERT_EQUAL(linphone_conference_get_participant_count(conference), 2, int, "%d"); } @@ -2966,12 +2972,13 @@ static void simple_conference_with_one_participant(void) { all_manangers_in_conf = bctbx_list_remove(all_manangers_in_conf, michelle); for (bctbx_list_t *it = all_manangers_in_conf; it; it = bctbx_list_next(it)) { LinphoneCoreManager *m = (LinphoneCoreManager *)bctbx_list_get_data(it); - - LinphoneAddress *uri = linphone_address_new(linphone_core_get_identity(m->lc)); + LinphoneAddress *m_uri = (linphone_core_conference_server_enabled(m->lc)) + ? linphone_address_clone(marie_conference_address) + : linphone_address_new(linphone_core_get_identity(m->lc)); LinphoneConference *conference = - linphone_core_search_conference(m->lc, NULL, uri, marie_conference_address, NULL); + linphone_core_search_conference(m->lc, NULL, m_uri, marie_conference_address, NULL); BC_ASSERT_PTR_NOT_NULL(conference); - linphone_address_unref(uri); + linphone_address_unref(m_uri); if (conference) { BC_ASSERT_EQUAL(linphone_conference_get_participant_count(conference), 1, int, "%d"); } @@ -4396,28 +4403,29 @@ static void simple_conference_with_file_player(void) { BC_ASSERT_TRUE(wait_for_list(lcs, &marie->stat.number_of_LinphoneCallStreamsRunning, 2 * no_participants, liblinphone_tester_sip_timeout)); - LinphoneAccount *marie_account = linphone_core_get_default_account(marie->lc); - LinphoneAddress *marie_addr = linphone_account_get_contact_address(marie_account); - LinphoneConference *l_conference = linphone_core_search_conference(marie->lc, NULL, marie_addr, NULL, NULL); + LinphoneConference *l_conference = linphone_core_get_conference(marie->lc); BC_ASSERT_PTR_NOT_NULL(l_conference); - BC_ASSERT_TRUE(linphone_conference_is_in(l_conference)); - BC_ASSERT_EQUAL(linphone_conference_get_participant_count(l_conference), no_unique_participants, int, "%d"); + if (l_conference) { + BC_ASSERT_TRUE(linphone_conference_is_in(l_conference)); + BC_ASSERT_EQUAL(linphone_conference_get_participant_count(l_conference), no_unique_participants, int, "%d"); - BC_ASSERT_PTR_NULL(linphone_core_get_current_call(marie->lc)); + BC_ASSERT_PTR_NULL(linphone_core_get_current_call(marie->lc)); - LinphonePlayer *player = linphone_conference_get_player(l_conference); - LinphonePlayerCbs *player_cbs = NULL; - BC_ASSERT_PTR_NOT_NULL(player); - if (player) { - player_cbs = linphone_factory_create_player_cbs(linphone_factory_get()); - linphone_player_cbs_set_eof_reached(player_cbs, on_eof); - linphone_player_cbs_set_user_data(player_cbs, marie); - linphone_player_add_callbacks(player, player_cbs); - linphone_core_set_record_file(pauline->lc, pauline_recordpath); - linphone_core_set_record_file(laure->lc, laure_recordpath); - linphone_core_set_record_file(michelle->lc, michelle_recordpath); - BC_ASSERT_EQUAL(linphone_player_open(player, hellopath), 0, int, "%d"); - BC_ASSERT_EQUAL(linphone_player_start(player), 0, int, "%d"); + LinphonePlayer *player = linphone_conference_get_player(l_conference); + LinphonePlayerCbs *player_cbs = NULL; + BC_ASSERT_PTR_NOT_NULL(player); + if (player) { + player_cbs = linphone_factory_create_player_cbs(linphone_factory_get()); + linphone_player_cbs_set_eof_reached(player_cbs, on_eof); + linphone_player_cbs_set_user_data(player_cbs, marie); + linphone_player_add_callbacks(player, player_cbs); + linphone_core_set_record_file(pauline->lc, pauline_recordpath); + linphone_core_set_record_file(laure->lc, laure_recordpath); + linphone_core_set_record_file(michelle->lc, michelle_recordpath); + BC_ASSERT_EQUAL(linphone_player_open(player, hellopath), 0, int, "%d"); + BC_ASSERT_EQUAL(linphone_player_start(player), 0, int, "%d"); + } + if (player_cbs) linphone_player_cbs_unref(player_cbs); } // The waiting duration must be at least as long as the wav file @@ -4427,13 +4435,12 @@ static void simple_conference_with_file_player(void) { terminate_conference(participants, marie, NULL, NULL, FALSE); - BC_ASSERT_PTR_NULL(linphone_core_search_conference(marie->lc, NULL, marie_addr, NULL, NULL)); + BC_ASSERT_PTR_NULL(linphone_core_get_conference(marie->lc)); BC_ASSERT_EQUAL((unsigned int)bctbx_list_size(linphone_core_get_calls(marie->lc)), 0, unsigned int, "%u"); bctbx_list_free(lcs); bctbx_list_free(participants); - if (player_cbs) linphone_player_cbs_unref(player_cbs); BC_ASSERT_TRUE(liblinphone_tester_check_recorded_audio(hellopath, pauline_recordpath)); BC_ASSERT_TRUE(liblinphone_tester_check_recorded_audio(hellopath, laure_recordpath)); BC_ASSERT_TRUE(liblinphone_tester_check_recorded_audio(hellopath, michelle_recordpath)); diff --git a/tester/db/chatroom_conference.db b/tester/db/chatroom_conference.db index 9e0927358cfcf1bb0a25206c98783d6ae21ad800..91e7585788b70c7fe2e5b709273ce1e8962f7a9c 100644 GIT binary patch delta 486 zcmXw!J!lj`6vt<7XLk1%XZ{94NL21dV!JxKdr8a%gm730ilj(oqg<4v&<)3lRmd$0 zwmG&9+NkY$?17abm0zHCDv>iH0YSm|(L^gJ>p9Jv_v8J4kJs81txd6Zn2xoN)aY3E z;ysLdVu#>8dPp!Tf6ABgzPuo3#7;MPChU2Slf+LymQ{MH9Aq=4=k$Olc8T1Rr_mR? znN-_?%`-D|^u!$ZO4ck*XG@2&`tdsfpb3+0f~Q!KZMoe|61jTT5`@wyqLFK!<?&F5 zfv->cp;kJoPE1uR6@x-wPx@h?^z=W(YH_1+eYtsgLDd&8HB}>yuhO~Jc{Z?3=Qg%) zGttP80u@Z{M<Z=eG_Zxiv1(<~Y+$wj5_My#xv1*#wJZM8f-w?8&b5;>=}LSH_(B-A z2!7)eeqbvbT7H3HhfzvBZsnD6W&%$3ZFS_}u!~*+d-#rb_>9+hg2(7(LwX(Kj?2x_ zF5|XiKE)y<j-3;W+dL;$`u47G3>yXf!7qHp2fV>6<Jd5U2PhA=xi+Ik${dpSCY|>d RzuE8H?sw>;ey1@0@Gqjgc69&% delta 180 zcmZoTz}s+ucY-vd=tLQ3M$wH4OZde&`K%fEZ}V^AZ{(NY`^0yaZz*3ipY_H@MZV3} zawi$NIQd)|_<r!Y^55Mopm3je;)DnmIc7)3$&PYTo0IkC8FDi)Ffj4gGVmYguiY$Y zP{=>IHopZT_>qDCC;!LIf(=jkH-D@b7T{swzrn!&gZ~5n4gTjqwI}!|-<Yoh6urm5 e|BL@K|7-qxK*i_yoA0e}zqg)o`@Qu{N*e%4_B{^( diff --git a/tester/local-conference-tester-functions.cpp b/tester/local-conference-tester-functions.cpp index 77e356dde7..99bd73cab7 100644 --- a/tester/local-conference-tester-functions.cpp +++ b/tester/local-conference-tester-functions.cpp @@ -1243,8 +1243,8 @@ void set_video_settings_in_conference(LinphoneCoreManager *focus, int, "%0d"); for (auto mgr : active_cores) { - LinphoneAddress *uri2 = mgr->identity; - LinphoneConference *pconference = linphone_core_search_conference(mgr->lc, NULL, uri2, confAddr, NULL); + const LinphoneAddress *local_address = (mgr == focus) ? confAddr : mgr->identity; + LinphoneConference *pconference = linphone_core_search_conference(mgr->lc, NULL, local_address, confAddr, NULL); BC_ASSERT_PTR_NOT_NULL(pconference); if (pconference) { LinphoneParticipant *p = (mgr == participant) @@ -2055,8 +2055,9 @@ void create_conference_base(time_t start_time, }); for (auto mgr : conferenceMgrs) { - LinphoneAddress *uri = mgr->identity; - LinphoneConference *pconference = linphone_core_search_conference(mgr->lc, NULL, uri, confAddr, NULL); + const LinphoneAddress *local_address = (mgr == focus.getCMgr()) ? confAddr : mgr->identity; + LinphoneConference *pconference = + linphone_core_search_conference(mgr->lc, NULL, local_address, confAddr, NULL); BC_ASSERT_PTR_NOT_NULL(pconference); if (pconference) { const LinphoneConferenceParams *conference_params = @@ -2361,9 +2362,9 @@ void create_conference_base(time_t start_time, bool pauline_expected_thumbnails_requested = are_participants_camera_streams_requested(pauline.getCMgr(), paulineConference); for (auto mgr : conferenceMgrs) { - const LinphoneAddress *uri = mgr->identity; + const LinphoneAddress *local_address = (mgr == focus.getCMgr()) ? confAddr : mgr->identity; LinphoneConference *pconference = - linphone_core_search_conference(mgr->lc, NULL, uri, confAddr, NULL); + linphone_core_search_conference(mgr->lc, NULL, local_address, confAddr, NULL); BC_ASSERT_PTR_NOT_NULL(pconference); if (pconference) { LinphoneParticipant *p = (mgr == pauline.getCMgr()) @@ -2517,8 +2518,9 @@ void create_conference_base(time_t start_time, liblinphone_tester_sip_timeout)); for (auto mgr : conferenceMgrs) { + const LinphoneAddress *local_address = (mgr == focus.getCMgr()) ? confAddr : mgr->identity; LinphoneConference *pconference = - linphone_core_search_conference(mgr->lc, NULL, mgr->identity, confAddr, NULL); + linphone_core_search_conference(mgr->lc, NULL, local_address, confAddr, NULL); BC_ASSERT_PTR_NOT_NULL(pconference); if (pconference) { if (mgr == pauline.getCMgr()) { @@ -2646,8 +2648,9 @@ void create_conference_base(time_t start_time, } for (auto mgr : conferenceMgrs) { + const LinphoneAddress *local_address = (mgr == focus.getCMgr()) ? confAddr : mgr->identity; LinphoneConference *pconference = - linphone_core_search_conference(mgr->lc, NULL, mgr->identity, confAddr, NULL); + linphone_core_search_conference(mgr->lc, NULL, local_address, confAddr, NULL); BC_ASSERT_PTR_NOT_NULL(pconference); if (pconference) { if (mgr == pauline.getCMgr()) { @@ -2759,8 +2762,9 @@ void create_conference_base(time_t start_time, } for (auto mgr : conferenceMgrs) { + const LinphoneAddress *local_address = (mgr == focus.getCMgr()) ? confAddr : mgr->identity; LinphoneConference *pconference = - linphone_core_search_conference(mgr->lc, NULL, mgr->identity, confAddr, NULL); + linphone_core_search_conference(mgr->lc, NULL, local_address, confAddr, NULL); BC_ASSERT_PTR_NOT_NULL(pconference); if (pconference) { auto info = linphone_conference_get_info(pconference); @@ -3114,8 +3118,9 @@ void create_conference_base(time_t start_time, : LinphoneParticipantDeviceStatePresent; size_t no_devices = static_cast<size_t>(no_local_participants + extra_participants); for (auto mgr : conferenceMgrs) { + const LinphoneAddress *local_address = (mgr == focus.getCMgr()) ? confAddr : mgr->identity; LinphoneConference *pconference = - linphone_core_search_conference(mgr->lc, NULL, mgr->identity, confAddr, NULL); + linphone_core_search_conference(mgr->lc, NULL, local_address, confAddr, NULL); if ((mgr == michelle.getCMgr()) && (participant_list_type == LinphoneConferenceParticipantListTypeClosed)) { BC_ASSERT_PTR_NULL(pconference); @@ -3513,8 +3518,9 @@ void create_conference_base(time_t start_time, } for (auto mgr : conferenceMgrs) { + const LinphoneAddress *local_address = (mgr == focus.getCMgr()) ? confAddr : mgr->identity; LinphoneConference *pconference = - linphone_core_search_conference(mgr->lc, NULL, mgr->identity, confAddr, NULL); + linphone_core_search_conference(mgr->lc, NULL, local_address, confAddr, NULL); if ((participant_list_type == LinphoneConferenceParticipantListTypeOpen) || ((mgr != berthe.getCMgr()) && (mgr != michelle.getCMgr()))) { BC_ASSERT_PTR_NOT_NULL(pconference); @@ -3885,8 +3891,9 @@ void create_conference_base(time_t start_time, } for (auto mgr : {focus.getCMgr(), marie.getCMgr(), michelle.getCMgr(), berthe.getCMgr()}) { + const LinphoneAddress *local_address = (mgr == focus.getCMgr()) ? confAddr : mgr->identity; LinphoneConference *pconference = - linphone_core_search_conference(mgr->lc, NULL, mgr->identity, confAddr, NULL); + linphone_core_search_conference(mgr->lc, NULL, local_address, confAddr, NULL); if (!remove_participant && (mgr == berthe.getCMgr())) { BC_ASSERT_PTR_NULL(pconference); } else { @@ -7172,7 +7179,7 @@ void create_conference_with_chat_base(LinphoneConferenceSecurityLevel security_l configure_end_to_end_encrypted_conference_server(focus); } LinphoneConference *fconference = - linphone_core_search_conference(focus.getLc(), NULL, focus.getIdentity().toC(), confAddr, NULL); + linphone_core_search_conference(focus.getLc(), NULL, confAddr, confAddr, NULL); BC_ASSERT_PTR_NOT_NULL(fconference); if (fconference) { LinphoneChatRoom *cr = linphone_conference_get_chat_room(fconference); @@ -8351,17 +8358,17 @@ void two_overlapping_conferences_base(bool_t same_organizer, bool_t dialout) { focus_stat.number_of_LinphoneCallStreamsRunning + 3, liblinphone_tester_sip_timeout)); - LinphoneAddress *focus_uri1 = focus.getCMgr()->identity; LinphoneConference *fconference1 = - linphone_core_search_conference(focus.getLc(), NULL, focus_uri1, confAddr1, NULL); + linphone_core_search_conference(focus.getLc(), NULL, confAddr1, confAddr1, NULL); BC_ASSERT_PTR_NOT_NULL(fconference1); // wait a bit more to detect side effect if any CoreManagerAssert({focus, marie, pauline, laure, michelle}).waitUntil(chrono::seconds(2), [] { return false; }); for (auto mgr : {focus.getCMgr(), marie.getCMgr(), pauline.getCMgr(), laure.getCMgr()}) { + const LinphoneAddress *local_address = (mgr == focus.getCMgr()) ? confAddr1 : mgr->identity; LinphoneConference *pconference = - linphone_core_search_conference(mgr->lc, NULL, mgr->identity, confAddr1, NULL); + linphone_core_search_conference(mgr->lc, NULL, local_address, confAddr1, NULL); BC_ASSERT_PTR_NOT_NULL(pconference); if (pconference) { const LinphoneConferenceParams *conference_params = linphone_conference_get_current_params(pconference); @@ -8620,14 +8627,14 @@ void two_overlapping_conferences_base(bool_t same_organizer, bool_t dialout) { BC_ASSERT_TRUE(wait_for_list(coresList, &pauline.getStats().number_of_participant_devices_on_hold, onhold, liblinphone_tester_sip_timeout)); - LinphoneAddress *focus_uri2 = focus.getCMgr()->identity; LinphoneConference *fconference2 = - linphone_core_search_conference(focus.getLc(), NULL, focus_uri2, confAddr2, NULL); + linphone_core_search_conference(focus.getLc(), NULL, confAddr2, confAddr2, NULL); BC_ASSERT_PTR_NOT_NULL(fconference2); for (auto mgr : {focus.getCMgr(), marie.getCMgr(), pauline.getCMgr(), laure.getCMgr()}) { + const LinphoneAddress *local_address = (mgr == focus.getCMgr()) ? confAddr1 : mgr->identity; LinphoneConference *pconference = - linphone_core_search_conference(mgr->lc, NULL, mgr->identity, confAddr1, NULL); + linphone_core_search_conference(mgr->lc, NULL, local_address, confAddr1, NULL); BC_ASSERT_PTR_NOT_NULL(pconference); if (pconference) { bctbx_list_t *devices = linphone_conference_get_participant_device_list(pconference); @@ -8785,8 +8792,9 @@ void two_overlapping_conferences_base(bool_t same_organizer, bool_t dialout) { focus_stat.number_of_LinphoneConferenceStateDeleted, int, "%d"); for (auto mgr : mgr_in_conf2) { + const LinphoneAddress *local_address = (mgr == focus.getCMgr()) ? confAddr2 : mgr->identity; LinphoneConference *pconference = - linphone_core_search_conference(mgr->lc, NULL, mgr->identity, confAddr2, NULL); + linphone_core_search_conference(mgr->lc, NULL, local_address, confAddr2, NULL); BC_ASSERT_PTR_NOT_NULL(pconference); if (pconference) { BC_ASSERT_EQUAL(linphone_conference_get_participant_count(pconference), @@ -8817,9 +8825,9 @@ void two_overlapping_conferences_base(bool_t same_organizer, bool_t dialout) { } } - LinphoneAddress *focusUri = focus.getCMgr()->identity; LinphoneConference *conference1 = - linphone_core_search_conference(focus.getLc(), NULL, focusUri, confAddr1, NULL); + linphone_core_search_conference(focus.getLc(), NULL, confAddr1, confAddr1, NULL); + BC_ASSERT_PTR_NOT_NULL(conference1); BC_ASSERT_TRUE(wait_for_list(coresList, &pauline.getStats().number_of_LinphoneCallPaused, pauline_stat.number_of_LinphoneCallPaused + 1, liblinphone_tester_sip_timeout)); @@ -8863,8 +8871,9 @@ void two_overlapping_conferences_base(bool_t same_organizer, bool_t dialout) { liblinphone_tester_sip_timeout)); for (auto mgr : mgr_in_conf2) { + const LinphoneAddress *local_address = (mgr == focus.getCMgr()) ? confAddr2 : mgr->identity; LinphoneConference *pconference = - linphone_core_search_conference(mgr->lc, NULL, mgr->identity, confAddr2, NULL); + linphone_core_search_conference(mgr->lc, NULL, local_address, confAddr2, NULL); BC_ASSERT_PTR_NOT_NULL(pconference); if (pconference) { BC_ASSERT_EQUAL(linphone_conference_get_participant_count(pconference), @@ -8888,35 +8897,38 @@ void two_overlapping_conferences_base(bool_t same_organizer, bool_t dialout) { pauline_stat = pauline.getStats(); stats laure_stat = laure.getStats(); int cnt = 0; - for (auto mgr : {laure.getCMgr(), pauline.getCMgr()}) { - cnt++; - LinphoneParticipant *participant = linphone_conference_find_participant(conference1, mgr->identity); - BC_ASSERT_PTR_NOT_NULL(participant); - if (participant) { - char *conference1_me = linphone_address_as_string( - linphone_participant_get_address(linphone_conference_get_me(conference1))); - ms_message("%s is removing participant %s from conference %s", conference1_me, - linphone_core_get_identity(mgr->lc), conference1_address_str); - ms_free(conference1_me); - linphone_conference_remove_participant_2(conference1, participant); + if (conference1) { + for (auto mgr : {laure.getCMgr(), pauline.getCMgr()}) { + cnt++; + LinphoneParticipant *participant = linphone_conference_find_participant(conference1, mgr->identity); + BC_ASSERT_PTR_NOT_NULL(participant); + if (participant) { + char *conference1_me = linphone_address_as_string( + linphone_participant_get_address(linphone_conference_get_me(conference1))); + ms_message("%s is removing participant %s from conference %s", conference1_me, + linphone_core_get_identity(mgr->lc), conference1_address_str); + ms_free(conference1_me); + linphone_conference_remove_participant_2(conference1, participant); + } + BC_ASSERT_TRUE(wait_for_list(coresList, &focus.getStats().number_of_LinphoneCallEnd, + focus_stat.number_of_LinphoneCallEnd + cnt, + liblinphone_tester_sip_timeout)); + BC_ASSERT_TRUE(wait_for_list(coresList, &focus.getStats().number_of_LinphoneCallReleased, + focus_stat.number_of_LinphoneCallReleased + cnt, + liblinphone_tester_sip_timeout)); + BC_ASSERT_TRUE(wait_for_list(coresList, &focus.getStats().number_of_participants_removed, + focus_stat.number_of_participants_removed + cnt, + liblinphone_tester_sip_timeout)); + BC_ASSERT_TRUE(wait_for_list(coresList, &focus.getStats().number_of_participant_devices_removed, + focus_stat.number_of_participant_devices_removed + cnt, + liblinphone_tester_sip_timeout)); + BC_ASSERT_TRUE(wait_for_list(coresList, &marie.getStats().number_of_participants_removed, + marie_stat.number_of_participants_removed + cnt, + liblinphone_tester_sip_timeout)); + BC_ASSERT_TRUE(wait_for_list(coresList, &marie.getStats().number_of_participant_devices_removed, + marie_stat.number_of_participant_devices_removed + cnt, + liblinphone_tester_sip_timeout)); } - BC_ASSERT_TRUE(wait_for_list(coresList, &focus.getStats().number_of_LinphoneCallEnd, - focus_stat.number_of_LinphoneCallEnd + cnt, liblinphone_tester_sip_timeout)); - BC_ASSERT_TRUE(wait_for_list(coresList, &focus.getStats().number_of_LinphoneCallReleased, - focus_stat.number_of_LinphoneCallReleased + cnt, - liblinphone_tester_sip_timeout)); - BC_ASSERT_TRUE(wait_for_list(coresList, &focus.getStats().number_of_participants_removed, - focus_stat.number_of_participants_removed + cnt, - liblinphone_tester_sip_timeout)); - BC_ASSERT_TRUE(wait_for_list(coresList, &focus.getStats().number_of_participant_devices_removed, - focus_stat.number_of_participant_devices_removed + cnt, - liblinphone_tester_sip_timeout)); - BC_ASSERT_TRUE(wait_for_list(coresList, &marie.getStats().number_of_participants_removed, - marie_stat.number_of_participants_removed + cnt, - liblinphone_tester_sip_timeout)); - BC_ASSERT_TRUE(wait_for_list(coresList, &marie.getStats().number_of_participant_devices_removed, - marie_stat.number_of_participant_devices_removed + cnt, - liblinphone_tester_sip_timeout)); } BC_ASSERT_TRUE(wait_for_list(coresList, &laure.getStats().number_of_LinphoneCallEnd, @@ -8998,8 +9010,9 @@ void two_overlapping_conferences_base(bool_t same_organizer, bool_t dialout) { liblinphone_tester_sip_timeout)); for (auto mgr : mgr_in_conf2) { + const LinphoneAddress *local_address = (mgr == focus.getCMgr()) ? confAddr2 : mgr->identity; LinphoneConference *pconference = - linphone_core_search_conference(mgr->lc, NULL, mgr->identity, confAddr2, NULL); + linphone_core_search_conference(mgr->lc, NULL, local_address, confAddr2, NULL); BC_ASSERT_PTR_NOT_NULL(pconference); if (pconference) { BC_ASSERT_EQUAL(linphone_conference_get_participant_count(pconference), @@ -9057,7 +9070,7 @@ void two_overlapping_conferences_base(bool_t same_organizer, bool_t dialout) { liblinphone_tester_sip_timeout)); LinphoneConference *conference2 = - linphone_core_search_conference(focus.getLc(), NULL, focusUri, confAddr2, NULL); + linphone_core_search_conference(focus.getLc(), NULL, confAddr2, confAddr2, NULL); BC_ASSERT_PTR_NULL(conference2); // Marie terminates conference1 (conference1 is destroyed on the server) @@ -10583,8 +10596,9 @@ void create_simple_conference_merging_calls_base(bool_t enable_ice, CoreManagerAssert({focus, marie, pauline, laure}).waitUntil(chrono::seconds(2), [] { return false; }); for (auto mgr : conferenceMgrs) { - LinphoneAddress *uri = mgr->identity; - LinphoneConference *pconference = linphone_core_search_conference(mgr->lc, NULL, uri, confAddr, NULL); + const LinphoneAddress *local_address = (mgr == focus.getCMgr()) ? confAddr : mgr->identity; + LinphoneConference *pconference = + linphone_core_search_conference(mgr->lc, NULL, local_address, confAddr, NULL); BC_ASSERT_PTR_NOT_NULL(pconference); if (pconference) { @@ -10676,9 +10690,8 @@ void create_simple_conference_merging_calls_base(bool_t enable_ice, // wait a bit more to detect side effect if any CoreManagerAssert({focus, marie, pauline, laure}).waitUntil(chrono::seconds(2), [] { return false; }); - LinphoneAddress *focus_addr = focus.getCMgr()->identity; LinphoneConference *fconference = - linphone_core_search_conference(focus.getLc(), NULL, focus_addr, confAddr, NULL); + linphone_core_search_conference(focus.getLc(), NULL, confAddr, confAddr, NULL); BC_ASSERT_PTR_NOT_NULL(fconference); for (auto mgr : members) { @@ -10816,8 +10829,9 @@ void create_simple_conference_merging_calls_base(bool_t enable_ice, } for (auto mgr : conferenceMgrs) { - LinphoneAddress *uri = mgr->identity; - LinphoneConference *pconference = linphone_core_search_conference(mgr->lc, NULL, uri, confAddr, NULL); + const LinphoneAddress *local_address = (mgr == focus.getCMgr()) ? confAddr : mgr->identity; + LinphoneConference *pconference = + linphone_core_search_conference(mgr->lc, NULL, local_address, confAddr, NULL); BC_ASSERT_PTR_NOT_NULL(pconference); if (pconference) { diff --git a/tester/local-scheduled-conference-tester.cpp b/tester/local-scheduled-conference-tester.cpp index 1d07499ca4..941c15791f 100644 --- a/tester/local-scheduled-conference-tester.cpp +++ b/tester/local-scheduled-conference-tester.cpp @@ -2719,7 +2719,7 @@ static void conference_with_screen_sharing_enabled_since_the_start(void) { if (!remaining_members.empty()) { LinphoneConference *conference = - linphone_core_search_conference(focus.getLc(), NULL, focus.getCMgr()->identity, confAddr, NULL); + linphone_core_search_conference(focus.getLc(), NULL, confAddr, confAddr, NULL); BC_ASSERT_PTR_NOT_NULL(conference); if (conference) { LinphoneParticipantDevice *screen_sharing_device = diff --git a/tester/main-db-tester.cpp b/tester/main-db-tester.cpp index 1b605bda1b..4e201744ce 100644 --- a/tester/main-db-tester.cpp +++ b/tester/main-db-tester.cpp @@ -423,10 +423,11 @@ static void load_a_lot_of_chatrooms_cleaning_gruu(void) { static void load_chatroom_conference_base(bool_t keep_gruu) { MainDbProvider provider("db/chatroom_conference.db", keep_gruu, TRUE); + BC_ASSERT_TRUE(linphone_core_gruu_in_conference_address_enabled(provider.getCoreManager()->lc) == keep_gruu); MainDb &mainDb = provider.getMainDb(); if (mainDb.isInitialized()) { list<shared_ptr<AbstractChatRoom>> chatRooms = mainDb.getChatRooms(); - BC_ASSERT_EQUAL(chatRooms.size(), 2, size_t, "%zu"); + BC_ASSERT_EQUAL(chatRooms.size(), 4, size_t, "%zu"); for (const auto &chatRoom : chatRooms) { const auto &conferenceAddress = chatRoom->getConferenceAddress(); // Basic chatroom do not have a conference address @@ -434,7 +435,7 @@ static void load_chatroom_conference_base(bool_t keep_gruu) { auto domain = conferenceAddress->getDomain(); BC_ASSERT_STRING_EQUAL(L_STRING_TO_C(domain), MainDbProvider::chatroom_domain); auto hasGruu = conferenceAddress->hasUriParam("gr"); - BC_ASSERT_TRUE(conferenceAddress->hasUriParam("gr") == !!keep_gruu); + BC_ASSERT_TRUE(hasGruu == !!keep_gruu); if (hasGruu) { auto gr = conferenceAddress->getUriParamValue("gr"); BC_ASSERT_STRING_EQUAL(L_STRING_TO_C(gr), MainDbProvider::chatroom_gr); @@ -442,6 +443,28 @@ static void load_chatroom_conference_base(bool_t keep_gruu) { } } + LinphoneAddress *local_address = linphone_address_new("sip:berthe_fmmz-@sip.example.org"); + LinphoneAddress *new_conference_address = linphone_address_new( + "sip:chloe_khumi@sip.example.org;gr=urn:uuid:459797d6-40f9-0072-a3ad-e9237e042437;conf-id=abcdef"); + LinphoneAddress *short_conference_address = + linphone_address_new("sip:chloe_khumi@sip.example.org;gr=urn:uuid:459797d6-40f9-0072-a3ad-e9237e042437"); + LinphoneAddress *long_conference_address = linphone_address_new( + "sip:chloe_khumi@sip.example.org;gr=urn:uuid:459797d6-40f9-0072-a3ad-e9237e042437;conf-id=CvN8Rr69~"); + BC_ASSERT_PTR_NOT_NULL(linphone_core_search_chat_room_2(provider.getCoreManager()->lc, NULL, local_address, + short_conference_address, NULL)); + BC_ASSERT_PTR_NOT_NULL(linphone_core_search_chat_room_2(provider.getCoreManager()->lc, NULL, local_address, + long_conference_address, NULL)); + // Verify that linphone_core_search_chat_room_2 doesn't do a SIP address comparison as stated in the RFC. In + // fact, doing that leads to being too exposed to server instabilities. For example, if a server for whatever + // reason removes the conf-id parameter from the chatroom peer address, it will prevent to client to join any + // new chatroom as all will match the corrupted chat + BC_ASSERT_PTR_NULL(linphone_core_search_chat_room_2(provider.getCoreManager()->lc, NULL, local_address, + new_conference_address, NULL)); + linphone_address_unref(local_address); + linphone_address_unref(new_conference_address); + linphone_address_unref(short_conference_address); + linphone_address_unref(long_conference_address); + list<shared_ptr<ConferenceInfo>> conferenceInfos = mainDb.getConferenceInfos(); BC_ASSERT_EQUAL(conferenceInfos.size(), 1, size_t, "%zu"); for (const auto &conferenceInfo : conferenceInfos) { diff --git a/tester/tester.c b/tester/tester.c index 0d4cc4ded4..20002d2631 100644 --- a/tester/tester.c +++ b/tester/tester.c @@ -2038,10 +2038,9 @@ static LinphoneStatus check_participant_removal(bctbx_list_t *lcs, (conf_initial_stats.number_of_LinphoneConferenceStateDeleted + 1), liblinphone_tester_sip_timeout)); - LinphoneAddress *conf_uri = linphone_address_new(linphone_core_get_identity(conf_mgr->lc)); - conference = linphone_core_search_conference(conf_mgr->lc, NULL, conf_uri, local_conference_address, NULL); + conference = linphone_core_search_conference(conf_mgr->lc, NULL, local_conference_address, + local_conference_address, NULL); BC_ASSERT_PTR_NULL(conference); - linphone_address_unref(conf_uri); } else { expected_no_participants = (participant_size - 1); -- GitLab