-
Andrea Gianarda authored
the remote contact address if not null when the call state is StreamRunning or Paused and the conference is in state Created or CreationPending Add "LeaksMemory" to "Core restarts as soon as chat room is created"
6c4a2572
/*
* 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 "bctoolbox/crypto.h"
#include <bctoolbox/defs.h>
#include "liblinphone_tester.h"
#include "linphone/api/c-chat-room-params.h"
#include "linphone/api/c-types.h"
#include "linphone/core.h"
#include "linphone/wrapper_utils.h"
#include "tester_utils.h"
#if __clang__ || ((__GNUC__ == 4 && __GNUC_MINOR__ >= 6) || __GNUC__ > 4)
#pragma GCC diagnostic push
#endif
#ifdef _MSC_VER
#pragma warning(disable : 4996)
#endif
const char *sFactoryUri = "sip:conference-factory@conf.example.org";
static bool_t wait_for_chat_room_participants(bctbx_list_t *lcs, LinphoneChatRoom *chat, int value, int timeout_ms) {
bctbx_list_t *iterator;
MSTimeSpec start;
liblinphone_tester_clock_start(&start);
while ((linphone_chat_room_get_nb_participants(chat) < value) &&
!liblinphone_tester_clock_elapsed(&start, timeout_ms)) {
for (iterator = lcs; iterator != NULL; iterator = iterator->next) {
linphone_core_iterate((LinphoneCore *)(iterator->data));
}
#ifdef LINPHONE_WINDOWS_UWP
{ bc_tester_process_events(); }
#elif defined(LINPHONE_WINDOWS_DESKTOP)
{
MSG msg;
while (PeekMessage(&msg, NULL, 0, 0, 1)) {
TranslateMessage(&msg);
DispatchMessage(&msg);
}
}
#endif
ms_usleep(20000);
}
if (linphone_chat_room_get_nb_participants(chat) < value) return FALSE;
else return TRUE;
}
void chat_room_session_state_changed(LinphoneChatRoom *cr, LinphoneCallState cstate, BCTBX_UNUSED(const char *msg)) {
LinphoneCore *lc = linphone_chat_room_get_core(cr);
stats *counters = get_stats(lc);
7172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140
switch (cstate) {
case LinphoneCallIncomingReceived:
counters->number_of_LinphoneChatRoomSessionIncomingReceived++;
break;
case LinphoneCallPushIncomingReceived:
counters->number_of_LinphoneChatRoomSessionPushIncomingReceived++;
break;
case LinphoneCallOutgoingInit:
counters->number_of_LinphoneChatRoomSessionOutgoingInit++;
break;
case LinphoneCallOutgoingProgress:
counters->number_of_LinphoneChatRoomSessionOutgoingProgress++;
break;
case LinphoneCallOutgoingRinging:
counters->number_of_LinphoneChatRoomSessionOutgoingRinging++;
break;
case LinphoneCallOutgoingEarlyMedia:
counters->number_of_LinphoneChatRoomSessionOutgoingEarlyMedia++;
break;
case LinphoneCallConnected:
counters->number_of_LinphoneChatRoomSessionConnected++;
break;
case LinphoneCallStreamsRunning:
counters->number_of_LinphoneChatRoomSessionStreamsRunning++;
break;
case LinphoneCallPausing:
counters->number_of_LinphoneChatRoomSessionPausing++;
break;
case LinphoneCallPaused:
counters->number_of_LinphoneChatRoomSessionPaused++;
break;
case LinphoneCallResuming:
counters->number_of_LinphoneChatRoomSessionResuming++;
break;
case LinphoneCallRefered:
counters->number_of_LinphoneChatRoomSessionRefered++;
break;
case LinphoneCallError:
counters->number_of_LinphoneChatRoomSessionError++;
break;
case LinphoneCallEnd:
counters->number_of_LinphoneChatRoomSessionEnd++;
break;
case LinphoneCallPausedByRemote:
counters->number_of_LinphoneChatRoomSessionPausedByRemote++;
break;
case LinphoneCallUpdatedByRemote:
counters->number_of_LinphoneChatRoomSessionUpdatedByRemote++;
break;
case LinphoneCallIncomingEarlyMedia:
counters->number_of_LinphoneChatRoomSessionIncomingEarlyMedia++;
break;
case LinphoneCallUpdating:
counters->number_of_LinphoneChatRoomSessionUpdating++;
break;
case LinphoneCallReleased:
counters->number_of_LinphoneChatRoomSessionReleased++;
break;
case LinphoneCallEarlyUpdating:
counters->number_of_LinphoneChatRoomSessionEarlyUpdating++;
break;
case LinphoneCallEarlyUpdatedByRemote:
counters->number_of_LinphoneChatRoomSessionEarlyUpdatedByRemote++;
break;
default:
BC_FAIL("unexpected event");
break;
}
}
141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210
static void chat_room_is_composing_received(LinphoneChatRoom *cr,
BCTBX_UNUSED(const LinphoneAddress *remoteAddr),
bool_t isComposing) {
LinphoneCore *core = linphone_chat_room_get_core(cr);
LinphoneCoreManager *manager = (LinphoneCoreManager *)linphone_core_get_user_data(core);
if (isComposing) manager->stat.number_of_LinphoneIsComposingActiveReceived++;
else manager->stat.number_of_LinphoneIsComposingIdleReceived++;
}
static void undecryptable_message_received(LinphoneChatRoom *room, BCTBX_UNUSED(LinphoneChatMessage *msg)) {
get_stats(linphone_chat_room_get_core(room))->number_of_LinphoneMessageUndecryptable++;
}
static void chat_room_participant_added(LinphoneChatRoom *cr, BCTBX_UNUSED(const LinphoneEventLog *event_log)) {
LinphoneCore *core = linphone_chat_room_get_core(cr);
LinphoneCoreManager *manager = (LinphoneCoreManager *)linphone_core_get_user_data(core);
manager->stat.number_of_participants_added++;
}
static void chat_room_participant_admin_status_changed(LinphoneChatRoom *cr,
BCTBX_UNUSED(const LinphoneEventLog *event_log)) {
LinphoneCore *core = linphone_chat_room_get_core(cr);
LinphoneCoreManager *manager = (LinphoneCoreManager *)linphone_core_get_user_data(core);
manager->stat.number_of_participant_admin_statuses_changed++;
}
static void chat_room_participant_removed(LinphoneChatRoom *cr, BCTBX_UNUSED(const LinphoneEventLog *event_log)) {
LinphoneCore *core = linphone_chat_room_get_core(cr);
LinphoneCoreManager *manager = (LinphoneCoreManager *)linphone_core_get_user_data(core);
manager->stat.number_of_participants_removed++;
}
static void chat_room_participant_device_added(LinphoneChatRoom *cr, BCTBX_UNUSED(const LinphoneEventLog *event_log)) {
LinphoneCore *core = linphone_chat_room_get_core(cr);
LinphoneCoreManager *manager = (LinphoneCoreManager *)linphone_core_get_user_data(core);
manager->stat.number_of_participant_devices_added++;
}
static void chat_room_participant_device_removed(LinphoneChatRoom *cr,
BCTBX_UNUSED(const LinphoneEventLog *event_log)) {
LinphoneCore *core = linphone_chat_room_get_core(cr);
LinphoneCoreManager *manager = (LinphoneCoreManager *)linphone_core_get_user_data(core);
manager->stat.number_of_participant_devices_removed++;
}
static void chat_room_state_changed(LinphoneChatRoom *cr, LinphoneChatRoomState newState) {
LinphoneCore *core = linphone_chat_room_get_core(cr);
LinphoneCoreManager *manager = (LinphoneCoreManager *)linphone_core_get_user_data(core);
const LinphoneAddress *addr = linphone_chat_room_get_conference_address(cr);
if (addr) {
char *addr_str = linphone_address_as_string(addr);
ms_message("ChatRoom [%s] state changed: %s", addr_str, linphone_chat_room_state_to_string(newState));
bctbx_free(addr_str);
}
switch (newState) {
case LinphoneChatRoomStateNone:
break;
case LinphoneChatRoomStateInstantiated:
manager->stat.number_of_LinphoneConferenceStateInstantiated++;
break;
case LinphoneChatRoomStateCreationPending:
manager->stat.number_of_LinphoneConferenceStateCreationPending++;
break;
case LinphoneChatRoomStateCreated:
manager->stat.number_of_LinphoneConferenceStateCreated++;
break;
case LinphoneChatRoomStateCreationFailed:
manager->stat.number_of_LinphoneConferenceStateCreationFailed++;
break;
211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280
case LinphoneChatRoomStateTerminationPending:
manager->stat.number_of_LinphoneConferenceStateTerminationPending++;
break;
case LinphoneChatRoomStateTerminated:
manager->stat.number_of_LinphoneConferenceStateTerminated++;
break;
case LinphoneChatRoomStateTerminationFailed:
manager->stat.number_of_LinphoneConferenceStateTerminationFailed++;
break;
case LinphoneChatRoomStateDeleted:
manager->stat.number_of_LinphoneConferenceStateDeleted++;
break;
default:
ms_error("Invalid ChatRoom state for Chatroom [%s] EndOfEnum is used ONLY as a guard",
linphone_address_as_string(addr));
break;
}
}
static void chat_room_security_event(LinphoneChatRoom *cr, const LinphoneEventLog *event_log) {
LinphoneCore *core = linphone_chat_room_get_core(cr);
LinphoneCoreManager *manager = (LinphoneCoreManager *)linphone_core_get_user_data(core);
switch (linphone_event_log_get_security_event_type(event_log)) {
case LinphoneSecurityEventTypeNone:
break;
case LinphoneSecurityEventTypeSecurityLevelDowngraded:
manager->stat.number_of_SecurityLevelDowngraded++;
break;
case LinphoneSecurityEventTypeParticipantMaxDeviceCountExceeded:
manager->stat.number_of_ParticipantMaxDeviceCountExceeded++;
break;
case LinphoneSecurityEventTypeEncryptionIdentityKeyChanged:
manager->stat.number_of_EncryptionIdentityKeyChanged++;
break;
case LinphoneSecurityEventTypeManInTheMiddleDetected:
manager->stat.number_of_ManInTheMiddleDetected++;
break;
}
}
static void chat_room_subject_changed(LinphoneChatRoom *cr, BCTBX_UNUSED(const LinphoneEventLog *event_log)) {
LinphoneCore *core = linphone_chat_room_get_core(cr);
LinphoneCoreManager *manager = (LinphoneCoreManager *)linphone_core_get_user_data(core);
manager->stat.number_of_subject_changed++;
}
static void chat_room_conference_joined(LinphoneChatRoom *cr, BCTBX_UNUSED(const LinphoneEventLog *event_log)) {
LinphoneCore *core = linphone_chat_room_get_core(cr);
LinphoneCoreManager *manager = (LinphoneCoreManager *)linphone_core_get_user_data(core);
manager->stat.number_of_LinphoneChatRoomConferenceJoined++;
}
static void chat_room_message_ephemeral(LinphoneChatRoom *cr, const LinphoneEventLog *event_log) {
LinphoneCore *core = linphone_chat_room_get_core(cr);
LinphoneCoreManager *manager = (LinphoneCoreManager *)linphone_core_get_user_data(core);
switch (linphone_event_log_get_type(event_log)) {
case LinphoneEventLogTypeConferenceEphemeralMessageLifetimeChanged:
manager->stat.number_of_LinphoneChatRoomEphemeralLifetimeChanged++;
break;
case LinphoneEventLogTypeConferenceEphemeralMessageEnabled:
manager->stat.number_of_LinphoneChatRoomEphemeralMessageEnabled++;
break;
case LinphoneEventLogTypeConferenceEphemeralMessageDisabled:
manager->stat.number_of_LinphoneChatRoomEphemeralMessageDisabled++;
break;
default:
break;
}
}
281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350
static void chat_room_message_ephemeral_started(LinphoneChatRoom *cr, BCTBX_UNUSED(const LinphoneEventLog *event_log)) {
LinphoneCore *core = linphone_chat_room_get_core(cr);
LinphoneCoreManager *manager = (LinphoneCoreManager *)linphone_core_get_user_data(core);
manager->stat.number_of_LinphoneChatRoomEphemeralTimerStarted++;
}
static void chat_room_message_ephemeral_deleted(LinphoneChatRoom *cr, BCTBX_UNUSED(const LinphoneEventLog *event_log)) {
LinphoneCore *core = linphone_chat_room_get_core(cr);
LinphoneCoreManager *manager = (LinphoneCoreManager *)linphone_core_get_user_data(core);
manager->stat.number_of_LinphoneChatRoomEphemeralDeleted++;
}
void setup_chat_room_callbacks(LinphoneChatRoomCbs *cbs) {
linphone_chat_room_cbs_set_session_state_changed(cbs, chat_room_session_state_changed);
linphone_chat_room_cbs_set_is_composing_received(cbs, chat_room_is_composing_received);
linphone_chat_room_cbs_set_participant_added(cbs, chat_room_participant_added);
linphone_chat_room_cbs_set_participant_admin_status_changed(cbs, chat_room_participant_admin_status_changed);
linphone_chat_room_cbs_set_participant_removed(cbs, chat_room_participant_removed);
linphone_chat_room_cbs_set_state_changed(cbs, chat_room_state_changed);
linphone_chat_room_cbs_set_security_event(cbs, chat_room_security_event);
linphone_chat_room_cbs_set_subject_changed(cbs, chat_room_subject_changed);
linphone_chat_room_cbs_set_participant_device_added(cbs, chat_room_participant_device_added);
linphone_chat_room_cbs_set_participant_device_removed(cbs, chat_room_participant_device_removed);
linphone_chat_room_cbs_set_undecryptable_message_received(cbs, undecryptable_message_received);
linphone_chat_room_cbs_set_conference_joined(cbs, chat_room_conference_joined);
linphone_chat_room_cbs_set_ephemeral_event(cbs, chat_room_message_ephemeral);
linphone_chat_room_cbs_set_ephemeral_message_timer_started(cbs, chat_room_message_ephemeral_started);
linphone_chat_room_cbs_set_ephemeral_message_deleted(cbs, chat_room_message_ephemeral_deleted);
}
void core_chat_room_state_changed(BCTBX_UNUSED(LinphoneCore *core), LinphoneChatRoom *cr, LinphoneChatRoomState state) {
if (state == LinphoneChatRoomStateInstantiated) {
LinphoneChatRoomCbs *cbs = linphone_factory_create_chat_room_cbs(linphone_factory_get());
setup_chat_room_callbacks(cbs);
linphone_chat_room_add_callbacks(cr, cbs);
linphone_chat_room_cbs_unref(cbs);
}
}
void core_chat_room_subject_changed(LinphoneCore *core, BCTBX_UNUSED(LinphoneChatRoom *cr)) {
LinphoneCoreManager *manager = (LinphoneCoreManager *)linphone_core_get_user_data(core);
manager->stat.number_of_core_chat_room_subject_changed++;
}
void configure_core_for_conference(LinphoneCore *core,
const char *username,
const LinphoneAddress *factoryAddr,
bool_t server) {
const char *identity = linphone_core_get_identity(core);
LinphoneAddress *addr = linphone_address_new(identity);
linphone_address_set_username(
addr, (username) ? username : linphone_address_get_username(addr)); // What's the point if !username?
char *newIdentity = linphone_address_as_string_uri_only(addr);
linphone_address_unref(addr);
linphone_core_set_primary_contact(core, newIdentity);
bctbx_free(newIdentity);
linphone_core_enable_conference_server(core, server);
linphone_core_enable_rtp_bundle(core, TRUE);
LinphoneAccount *account = linphone_core_get_default_account(core);
const LinphoneAccountParams *account_params = linphone_account_get_params(account);
LinphoneAccountParams *new_account_params = linphone_account_params_clone(account_params);
linphone_account_params_enable_rtp_bundle(new_account_params, TRUE);
linphone_account_set_params(account, new_account_params);
linphone_account_params_unref(new_account_params);
BC_ASSERT_TRUE(linphone_account_params_rtp_bundle_enabled(linphone_account_get_params(account)));
if (factoryAddr) {
char *factoryUri = linphone_address_as_string(factoryAddr);
LinphoneProxyConfig *proxy = linphone_core_get_default_proxy_config(core);
linphone_proxy_config_edit(proxy);
351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420
linphone_proxy_config_set_conference_factory_uri(proxy, factoryUri);
linphone_proxy_config_done(proxy);
bctbx_free(factoryUri);
}
}
void _configure_core_for_conference(LinphoneCoreManager *lcm, const LinphoneAddress *factoryAddr) {
configure_core_for_conference(lcm->lc, NULL, factoryAddr, FALSE);
}
void _configure_core_for_audio_video_conference(LinphoneCoreManager *lcm, const LinphoneAddress *factoryAddr) {
if (factoryAddr) {
LinphoneAccount *account = linphone_core_get_default_account(lcm->lc);
LinphoneAccountParams *params = linphone_account_params_clone(linphone_account_get_params(account));
linphone_account_params_set_audio_video_conference_factory_address(params, factoryAddr);
linphone_account_set_params(account, params);
linphone_account_params_unref(params);
}
}
void configure_core_for_callbacks(LinphoneCoreManager *lcm, LinphoneCoreCbs *cbs) {
// Remove is-composing callback from the core, we use our own on the chat room
linphone_core_cbs_set_is_composing_received(lcm->cbs, NULL);
linphone_core_add_callbacks(lcm->lc, cbs);
linphone_core_set_user_data(lcm->lc, lcm);
}
void _start_core(LinphoneCoreManager *lcm) {
linphone_core_manager_start(lcm, TRUE);
}
LinphoneChatMessage *_send_message_ephemeral(LinphoneChatRoom *chatRoom, const char *message, bool_t isEphemeral) {
LinphoneChatMessage *msg = linphone_chat_room_create_message_from_utf8(chatRoom, message);
LinphoneChatMessageCbs *msgCbs = linphone_chat_message_get_callbacks(msg);
linphone_chat_message_cbs_set_msg_state_changed(msgCbs, liblinphone_tester_chat_message_msg_state_changed);
if (isEphemeral) {
linphone_chat_message_cbs_set_ephemeral_message_timer_started(
msgCbs, liblinphone_tester_chat_message_ephemeral_timer_started);
linphone_chat_message_cbs_set_ephemeral_message_deleted(msgCbs,
liblinphone_tester_chat_message_ephemeral_deleted);
}
linphone_chat_message_send(msg);
return msg;
}
LinphoneChatMessage *_send_message(LinphoneChatRoom *chatRoom, const char *message) {
return _send_message_ephemeral(chatRoom, message, FALSE);
}
static void fill_content_buffer(LinphoneContent *content, const char *sendFilePath) {
FILE *file_to_send = NULL;
size_t file_size;
file_to_send = fopen(sendFilePath, "rb");
BC_ASSERT_PTR_NOT_NULL(file_to_send);
fseek(file_to_send, 0, SEEK_END);
file_size = ftell(file_to_send);
fseek(file_to_send, 0, SEEK_SET);
uint8_t *buf = ms_malloc(file_size);
size_t read = fread(buf, sizeof(uint8_t), file_size, file_to_send);
BC_ASSERT_EQUAL((int)read, (int)file_size, int, "%d");
linphone_content_set_buffer(content, buf, file_size);
linphone_content_set_size(content, file_size); /*total size to be transfered*/
fclose(file_to_send);
}
void _send_file_plus_text(
421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490
LinphoneChatRoom *cr, const char *sendFilepath, const char *sendFilepath2, const char *text, bool_t use_buffer) {
LinphoneChatMessage *msg;
LinphoneChatMessageCbs *cbs;
LinphoneContent *content = linphone_core_create_content(linphone_chat_room_get_core(cr));
belle_sip_object_set_name(BELLE_SIP_OBJECT(content), "sintel trailer content");
linphone_content_set_type(content, "video");
linphone_content_set_subtype(content, "mkv");
linphone_content_set_name(content, "sintel_trailer_opus_h264.mkv");
if (use_buffer) {
fill_content_buffer(content, sendFilepath);
} else {
linphone_content_set_file_path(content, sendFilepath);
}
msg = linphone_chat_room_create_empty_message(cr);
linphone_chat_message_add_file_content(msg, content);
linphone_content_unref(content);
if (text) linphone_chat_message_add_utf8_text_content(msg, text);
if (sendFilepath2) {
LinphoneContent *content2 = linphone_core_create_content(linphone_chat_room_get_core(cr));
belle_sip_object_set_name(BELLE_SIP_OBJECT(content2), "ahbahouaismaisbon content");
linphone_content_set_type(content2, "audio");
linphone_content_set_subtype(content2, "wav");
linphone_content_set_name(content2, "ahbahouaismaisbon.wav");
if (use_buffer) {
fill_content_buffer(content2, sendFilepath2);
} else {
linphone_content_set_file_path(content2, sendFilepath2);
}
linphone_chat_message_add_file_content(msg, content2);
linphone_content_unref(content2);
}
cbs = linphone_factory_create_chat_message_cbs(linphone_factory_get());
linphone_chat_message_cbs_set_file_transfer_send_chunk(cbs, tester_file_transfer_send_2);
linphone_chat_message_cbs_set_msg_state_changed(cbs, liblinphone_tester_chat_message_msg_state_changed);
linphone_chat_message_cbs_set_file_transfer_progress_indication(cbs, file_transfer_progress_indication_2);
linphone_chat_message_add_callbacks(msg, cbs);
linphone_chat_message_cbs_unref(cbs);
linphone_chat_message_send(msg);
linphone_chat_message_unref(msg);
}
void _send_file(LinphoneChatRoom *cr, const char *sendFilepath, const char *sendFilepath2, bool_t use_buffer) {
_send_file_plus_text(cr, sendFilepath, sendFilepath2, NULL, use_buffer);
}
void _receive_file_plus_text(bctbx_list_t *coresList,
LinphoneCoreManager *lcm,
stats *receiverStats,
const char *receive_filepath,
const char *sendFilepath,
const char *sendFilepath2,
const char *text,
bool_t use_buffer) {
if (BC_ASSERT_TRUE(wait_for_list(coresList, &lcm->stat.number_of_LinphoneMessageReceivedWithFile,
receiverStats->number_of_LinphoneMessageReceivedWithFile + 1,
liblinphone_tester_sip_timeout))) {
LinphoneChatMessageCbs *cbs;
LinphoneChatMessage *msg = lcm->stat.last_received_chat_message;
const char *downloaded_file = NULL;
if (!use_buffer) {
downloaded_file = receive_filepath;
}
if (text) {
491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560
BC_ASSERT_TRUE(linphone_chat_message_has_text_content(msg));
BC_ASSERT_STRING_EQUAL(linphone_chat_message_get_utf8_text(msg), text);
}
cbs = linphone_chat_message_get_callbacks(msg);
linphone_chat_message_cbs_set_msg_state_changed(cbs, liblinphone_tester_chat_message_msg_state_changed);
linphone_chat_message_cbs_set_file_transfer_recv(cbs, file_transfer_received);
linphone_chat_message_cbs_set_file_transfer_progress_indication(cbs, file_transfer_progress_indication_2);
BC_ASSERT_PTR_NOT_NULL(linphone_chat_message_get_external_body_url(msg));
LinphoneContent *fileTransferContent = linphone_chat_message_get_file_transfer_information(msg);
BC_ASSERT_TRUE(linphone_content_is_file_transfer(fileTransferContent));
if (!use_buffer) {
linphone_content_set_file_path(fileTransferContent, downloaded_file);
}
linphone_chat_message_download_content(msg, fileTransferContent);
BC_ASSERT_EQUAL(linphone_chat_message_get_state(msg), LinphoneChatMessageStateFileTransferInProgress, int,
"%d");
// Cancel the download
wait_for_list(coresList, NULL, 0, 400);
char *downloaded_file_temp = bctbx_concat(downloaded_file, ".copy", NULL);
remove(downloaded_file_temp);
liblinphone_tester_copy_file(downloaded_file, downloaded_file_temp);
linphone_chat_message_cancel_file_transfer(msg);
liblinphone_tester_copy_file(downloaded_file_temp, downloaded_file);
remove(downloaded_file_temp);
bctbx_free(downloaded_file_temp);
linphone_chat_message_download_content(msg, fileTransferContent);
if (BC_ASSERT_TRUE(wait_for_list(coresList, &lcm->stat.number_of_LinphoneMessageFileTransferDone,
receiverStats->number_of_LinphoneMessageFileTransferDone + 1,
liblinphone_tester_sip_timeout))) {
if (use_buffer) {
// file_transfer_received function store file name into file_transfer_filepath
downloaded_file = bctbx_strdup(linphone_chat_message_get_file_transfer_filepath(msg));
}
compare_files(sendFilepath, downloaded_file);
}
if (sendFilepath2) {
remove(downloaded_file);
LinphoneContent *fileTransferContent2 = linphone_chat_message_get_file_transfer_information(msg);
BC_ASSERT_TRUE(linphone_content_is_file_transfer(fileTransferContent2));
if (!use_buffer) {
linphone_content_set_file_path(fileTransferContent2, downloaded_file);
}
linphone_chat_message_download_content(msg, fileTransferContent2);
BC_ASSERT_EQUAL(linphone_chat_message_get_state(msg), LinphoneChatMessageStateFileTransferInProgress, int,
"%d");
if (BC_ASSERT_TRUE(wait_for_list(coresList, &lcm->stat.number_of_LinphoneMessageFileTransferDone,
receiverStats->number_of_LinphoneMessageFileTransferDone + 2,
liblinphone_tester_sip_timeout))) {
if (use_buffer) {
// file_transfer_received function store file name into file_transfer_filepath
downloaded_file = bctbx_strdup(linphone_chat_message_get_file_transfer_filepath(msg));
}
compare_files(sendFilepath2, downloaded_file);
}
}
}
}
void _receive_file(bctbx_list_t *coresList,
LinphoneCoreManager *lcm,
stats *receiverStats,
const char *receive_filepath,
const char *sendFilepath,
561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630
const char *sendFilepath2,
bool_t use_buffer) {
_receive_file_plus_text(coresList, lcm, receiverStats, receive_filepath, sendFilepath, sendFilepath2, NULL,
use_buffer);
}
// Configure list of core manager for conference and add the listener
static bctbx_list_t *_init_core_for_conference_with_factory_uri(bctbx_list_t *coreManagerList,
const char *factoryUri,
const char *groupchat_version) {
LinphoneAddress *factoryAddr = linphone_address_new(factoryUri);
bctbx_list_for_each2(coreManagerList, (void (*)(void *, void *))_configure_core_for_conference,
(void *)factoryAddr);
linphone_address_unref(factoryAddr);
if (groupchat_version) {
bctbx_list_t *it;
char *spec = bctbx_strdup_printf("groupchat/%s", groupchat_version);
for (it = coreManagerList; it != NULL; it = it->next) {
LinphoneCoreManager *mgr = (LinphoneCoreManager *)it->data;
linphone_core_remove_linphone_spec(mgr->lc, "groupchat");
linphone_core_add_linphone_spec(mgr->lc, spec);
}
bctbx_free(spec);
}
LinphoneCoreCbs *cbs = linphone_factory_create_core_cbs(linphone_factory_get());
linphone_core_cbs_set_chat_room_state_changed(cbs, core_chat_room_state_changed);
linphone_core_cbs_set_chat_room_subject_changed(cbs, core_chat_room_subject_changed);
bctbx_list_for_each2(coreManagerList, (void (*)(void *, void *))configure_core_for_callbacks, (void *)cbs);
linphone_core_cbs_unref(cbs);
bctbx_list_t *coresList = NULL;
bctbx_list_t *item = coreManagerList;
for (item = coreManagerList; item; item = bctbx_list_next(item))
coresList = bctbx_list_append(coresList, ((LinphoneCoreManager *)(bctbx_list_get_data(item)))->lc);
return coresList;
}
bctbx_list_t *init_core_for_conference_with_factory_uri(bctbx_list_t *coreManagerList, const char *factoryUri) {
return _init_core_for_conference_with_factory_uri(coreManagerList, factoryUri, NULL);
}
bctbx_list_t *init_core_for_conference(bctbx_list_t *coreManagerList) {
return init_core_for_conference_with_factory_uri(coreManagerList, sFactoryUri);
}
bctbx_list_t *init_core_for_conference_with_groupchat_version(bctbx_list_t *coreManagerList,
const char *groupchat_version) {
return _init_core_for_conference_with_factory_uri(coreManagerList, sFactoryUri, groupchat_version);
}
void start_core_for_conference(bctbx_list_t *coreManagerList) {
bctbx_list_for_each(coreManagerList, (void (*)(void *))_start_core);
}
static LinphoneChatRoom *check_has_chat_room_client_side(bctbx_list_t *lcs,
LinphoneCoreManager *lcm,
BCTBX_UNUSED(stats *initialStats),
const LinphoneAddress *confAddr,
const char *subject,
int participantNumber,
bool_t isAdmin) {
char *deviceIdentity = linphone_core_get_device_identity(lcm->lc);
LinphoneAddress *localAddr = linphone_address_new(deviceIdentity);
bctbx_free(deviceIdentity);
LinphoneChatRoom *chatRoom = linphone_core_find_chat_room(lcm->lc, confAddr, localAddr);
linphone_address_unref(localAddr);
BC_ASSERT_PTR_NOT_NULL(chatRoom);
if (chatRoom) {
631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700
BC_ASSERT_TRUE(
wait_for_chat_room_participants(lcs, chatRoom, participantNumber, liblinphone_tester_sip_timeout));
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(chatRoom), participantNumber, int, "%d");
LinphoneParticipant *participant = linphone_chat_room_get_me(chatRoom);
BC_ASSERT_PTR_NOT_NULL(participant);
if (!(linphone_chat_room_get_capabilities(chatRoom) & LinphoneChatRoomCapabilitiesOneToOne))
BC_ASSERT(isAdmin == linphone_participant_is_admin(participant));
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(chatRoom), subject);
if (linphone_chat_room_get_capabilities(chatRoom) & LinphoneChatRoomCapabilitiesBasic) {
BC_ASSERT_FALSE(linphone_chat_room_can_handle_participants(chatRoom));
} else {
BC_ASSERT_TRUE(linphone_chat_room_can_handle_participants(chatRoom));
}
}
return chatRoom;
}
LinphoneChatRoom *check_creation_chat_room_client_side(bctbx_list_t *lcs,
LinphoneCoreManager *lcm,
stats *initialStats,
const LinphoneAddress *confAddr,
const char *subject,
int participantNumber,
bool_t isAdmin) {
BC_ASSERT_TRUE(wait_for_list(lcs, &lcm->stat.number_of_LinphoneConferenceStateCreationPending,
initialStats->number_of_LinphoneConferenceStateCreationPending + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(lcs, &lcm->stat.number_of_LinphoneConferenceStateCreated,
initialStats->number_of_LinphoneConferenceStateCreated + 1,
liblinphone_tester_sip_timeout));
if (linphone_core_is_network_reachable(lcm->lc)) {
BC_ASSERT_TRUE(wait_for_list(lcs, &lcm->stat.number_of_LinphoneChatRoomConferenceJoined,
initialStats->number_of_LinphoneChatRoomConferenceJoined + 1,
liblinphone_tester_sip_timeout));
}
return check_has_chat_room_client_side(lcs, lcm, initialStats, confAddr, subject, participantNumber, isAdmin);
}
void check_create_chat_room_client_side(bctbx_list_t *lcs,
LinphoneCoreManager *lcm,
LinphoneChatRoom *chatRoom,
stats *initialStats,
bctbx_list_t *participantsAddresses,
const char *initialSubject,
int expectedParticipantSize) {
const LinphoneChatRoomParams *params = linphone_chat_room_get_current_params(chatRoom);
BC_ASSERT_TRUE(wait_for_list(lcs, &lcm->stat.number_of_LinphoneConferenceStateInstantiated,
initialStats->number_of_LinphoneConferenceStateInstantiated + 1, 100));
BC_ASSERT_PTR_NOT_NULL(params);
if (linphone_chat_room_params_encryption_enabled(params)) {
BC_ASSERT_EQUAL(linphone_chat_room_get_security_level(chatRoom), LinphoneChatRoomSecurityLevelEncrypted,
LinphoneChatRoomSecurityLevel, "%i");
BC_ASSERT_TRUE(linphone_chat_room_get_capabilities(chatRoom) & LinphoneChatRoomCapabilitiesEncrypted);
}
// Check that the chat room is correctly created on Marie's side and that the participants are added
BC_ASSERT_TRUE(wait_for_list(lcs, &lcm->stat.number_of_LinphoneConferenceStateCreationPending,
initialStats->number_of_LinphoneConferenceStateCreationPending + 1,
liblinphone_tester_sip_timeout));
LinphoneParticipant *participant = linphone_chat_room_get_me(chatRoom);
BC_ASSERT_PTR_NOT_NULL(participant);
if (expectedParticipantSize == 0) {
BC_ASSERT_TRUE(wait_for_list(lcs, &lcm->stat.number_of_LinphoneConferenceStateCreationFailed,
initialStats->number_of_LinphoneConferenceStateCreationFailed + 1,
liblinphone_tester_sip_timeout));
if (participant) BC_ASSERT_FALSE(linphone_participant_is_admin(participant));
} else {
701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770
if (linphone_core_is_network_reachable(lcm->lc)) {
BC_ASSERT_TRUE(wait_for_list(lcs, &lcm->stat.number_of_LinphoneConferenceStateCreated,
initialStats->number_of_LinphoneConferenceStateCreated + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(lcs, &lcm->stat.number_of_LinphoneChatRoomConferenceJoined,
initialStats->number_of_LinphoneChatRoomConferenceJoined + 1,
liblinphone_tester_sip_timeout));
// FIXME: Small hack to handle situation where the core resubscribes to the chat room
wait_for_list(lcs, NULL, 0, 1000);
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(chatRoom),
(expectedParticipantSize >= 0) ? expectedParticipantSize
: ((int)bctbx_list_size(participantsAddresses)),
int, "%d");
if (participant) BC_ASSERT_TRUE(linphone_participant_is_admin(participant));
}
}
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(chatRoom), initialSubject);
if (linphone_chat_room_get_capabilities(chatRoom) & LinphoneChatRoomCapabilitiesBasic) {
BC_ASSERT_FALSE(linphone_chat_room_can_handle_participants(chatRoom));
} else {
BC_ASSERT_TRUE(linphone_chat_room_can_handle_participants(chatRoom));
}
bctbx_list_free_with_data(participantsAddresses, (bctbx_list_free_func)linphone_address_unref);
participantsAddresses = NULL;
}
LinphoneChatRoom *create_chat_room_client_side_with_params(bctbx_list_t *lcs,
LinphoneCoreManager *lcm,
stats *initialStats,
bctbx_list_t *participantsAddresses,
const char *initialSubject,
LinphoneChatRoomParams *params) {
LinphoneChatRoom *chatRoom =
linphone_core_create_chat_room_2(lcm->lc, params, initialSubject, participantsAddresses);
check_create_chat_room_client_side(lcs, lcm, chatRoom, initialStats, participantsAddresses, initialSubject,
(int)bctbx_list_size(participantsAddresses));
linphone_chat_room_unref(chatRoom);
return chatRoom;
}
LinphoneChatRoom *
create_chat_room_client_side_with_expected_number_of_participants(bctbx_list_t *lcs,
LinphoneCoreManager *lcm,
stats *initialStats,
bctbx_list_t *participantsAddresses,
const char *initialSubject,
int expectedParticipantSize,
bool_t encrypted,
LinphoneChatRoomEphemeralMode mode) {
int participantsAddressesSize = (int)bctbx_list_size(participantsAddresses);
LinphoneChatRoomParams *params = linphone_core_create_default_chat_room_params(lcm->lc);
linphone_chat_room_params_enable_encryption(params, encrypted);
linphone_chat_room_params_set_ephemeral_mode(params, mode);
linphone_chat_room_params_set_backend(params, LinphoneChatRoomBackendFlexisipChat);
linphone_chat_room_params_enable_group(params, participantsAddressesSize > 1 ? TRUE : FALSE);
LinphoneChatRoom *chatRoom =
linphone_core_create_chat_room_2(lcm->lc, params, initialSubject, participantsAddresses);
linphone_chat_room_params_unref(params);
if (!chatRoom) return NULL;
771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840
check_create_chat_room_client_side(lcs, lcm, chatRoom, initialStats, participantsAddresses, initialSubject,
expectedParticipantSize);
linphone_chat_room_unref(chatRoom);
return chatRoom;
}
LinphoneChatRoom *create_chat_room_with_params(bctbx_list_t *lcs,
LinphoneCoreManager *lcm,
stats *initialStats,
bctbx_list_t *participantsAddresses,
const char *initialSubject,
LinphoneChatRoomParams *params) {
int participantsAddressesSize = (int)bctbx_list_size(participantsAddresses);
if (!params) return NULL;
LinphoneChatRoom *chatRoom =
linphone_core_create_chat_room_2(lcm->lc, params, initialSubject, participantsAddresses);
check_create_chat_room_client_side(lcs, lcm, chatRoom, initialStats, participantsAddresses, initialSubject,
participantsAddressesSize);
linphone_chat_room_unref(chatRoom);
return chatRoom;
}
LinphoneChatRoom *create_chat_room_client_side(bctbx_list_t *lcs,
LinphoneCoreManager *lcm,
stats *initialStats,
bctbx_list_t *participantsAddresses,
const char *initialSubject,
bool_t encrypted,
LinphoneChatRoomEphemeralMode mode) {
return create_chat_room_client_side_with_expected_number_of_participants(
lcs, lcm, initialStats, participantsAddresses, initialSubject, (int)bctbx_list_size(participantsAddresses),
encrypted, mode);
}
static void group_chat_room_params(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *chloe = linphone_core_manager_create("chloe_rc");
bctbx_list_t *coresManagerList = bctbx_list_append(NULL, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
coresManagerList = bctbx_list_append(coresManagerList, chloe);
bctbx_list_t *participantsAddresses = NULL;
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
LinphoneChatRoom *marieCr = NULL;
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
LinphoneChatRoomParams *params = linphone_core_create_default_chat_room_params(marie->lc);
// Should create a basic chatroom
linphone_chat_room_params_enable_encryption(params, FALSE);
linphone_chat_room_params_set_backend(params, LinphoneChatRoomBackendBasic);
linphone_chat_room_params_enable_group(params, FALSE);
marieCr = linphone_core_create_chat_room_2(marie->lc, params, "Basic chat room subject", participantsAddresses);
BC_ASSERT_PTR_NOT_NULL(marieCr);
if (marieCr) {
BC_ASSERT_PTR_NOT_NULL(linphone_chat_room_get_current_params(marieCr));
BC_ASSERT_TRUE(linphone_chat_room_get_capabilities(marieCr) & LinphoneChatRoomCapabilitiesBasic);
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910
linphone_chat_room_unref(marieCr);
}
// Should create a one-to-one flexisip chat
linphone_chat_room_params_set_backend(params, LinphoneChatRoomBackendFlexisipChat);
linphone_chat_room_params_enable_group(params, FALSE);
marieCr = linphone_core_create_chat_room_2(marie->lc, params, "One to one client group chat room subject",
participantsAddresses);
BC_ASSERT_PTR_NOT_NULL(marieCr);
if (marieCr) {
BC_ASSERT_TRUE(linphone_chat_room_get_capabilities(marieCr) & LinphoneChatRoomCapabilitiesConference);
BC_ASSERT_TRUE(linphone_chat_room_get_capabilities(marieCr) & LinphoneChatRoomCapabilitiesOneToOne);
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
linphone_chat_room_unref(marieCr);
}
// Should create a group flexisip chat
linphone_chat_room_params_set_backend(params, LinphoneChatRoomBackendFlexisipChat);
linphone_chat_room_params_enable_group(params, TRUE);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(chloe->lc)));
marieCr = linphone_core_create_chat_room_2(marie->lc, params, "Group chat room subject", participantsAddresses);
BC_ASSERT_PTR_NOT_NULL(marieCr);
if (marieCr) {
BC_ASSERT_TRUE(linphone_chat_room_get_capabilities(marieCr) & LinphoneChatRoomCapabilitiesConference);
BC_ASSERT_FALSE(linphone_chat_room_get_capabilities(marieCr) & LinphoneChatRoomCapabilitiesOneToOne);
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
linphone_chat_room_unref(marieCr);
}
// Should create an encrypted group flexisip chat
linphone_chat_room_params_set_backend(params, LinphoneChatRoomBackendFlexisipChat);
linphone_chat_room_params_enable_group(params, TRUE);
linphone_chat_room_params_enable_encryption(params, TRUE);
// Check that enabling encryption also defines a valid encryptionBackend
BC_ASSERT_EQUAL(linphone_chat_room_params_get_encryption_backend(params), LinphoneChatRoomEncryptionBackendLime,
int, "%d");
marieCr =
linphone_core_create_chat_room_2(marie->lc, params, "Encrypted group chat room subject", participantsAddresses);
BC_ASSERT_PTR_NOT_NULL(marieCr);
if (marieCr) {
BC_ASSERT_TRUE(linphone_chat_room_get_capabilities(marieCr) & LinphoneChatRoomCapabilitiesConference);
BC_ASSERT_TRUE(linphone_chat_room_get_capabilities(marieCr) & LinphoneChatRoomCapabilitiesEncrypted);
BC_ASSERT_FALSE(linphone_chat_room_get_capabilities(marieCr) & LinphoneChatRoomCapabilitiesOneToOne);
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
linphone_chat_room_unref(marieCr);
}
// Should return NULL because params are invalid
linphone_chat_room_params_enable_group(params, TRUE);
linphone_chat_room_params_set_backend(params, LinphoneChatRoomBackendBasic); // Group + basic backend = invalid
BC_ASSERT_FALSE(linphone_chat_room_params_is_valid(params));
marieCr = linphone_core_create_chat_room_2(marie->lc, params, "Invalid chat room subject", NULL);
BC_ASSERT_PTR_NULL(marieCr);
if (marieCr) linphone_chat_room_unref(marieCr);
// Should set FlexisipChat as backend if encryption is enabled.
linphone_chat_room_params_set_backend(params, LinphoneChatRoomBackendBasic);
linphone_chat_room_params_enable_encryption(params, TRUE);
BC_ASSERT_EQUAL(linphone_chat_room_params_get_backend(params), LinphoneChatRoomBackendFlexisipChat, int, "%d");
// Cleanup
linphone_chat_room_params_unref(params);
bctbx_list_free_with_data(participantsAddresses, (bctbx_list_free_func)linphone_address_unref);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980
linphone_core_manager_destroy(chloe);
}
static void group_chat_room_creation_core_restart(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *laure = linphone_core_manager_create("laure_tcp_rc");
int dummy = 0;
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
LinphoneAddress *confAddr = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
coresManagerList = bctbx_list_append(coresManagerList, laure);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(laure->lc)));
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
stats initialLaureStats = laure->stat;
// Marie creates a new group chat room
LinphoneProxyConfig *proxy = linphone_core_get_default_proxy_config(marie->lc);
LinphoneAddress *marieAddr = linphone_address_new(linphone_proxy_config_get_identity(proxy));
const char *initialSubject = "Colleagues";
LinphoneChatRoomParams *params = linphone_core_create_default_chat_room_params(marie->lc);
linphone_chat_room_params_enable_encryption(params, FALSE);
linphone_chat_room_params_set_backend(params, LinphoneChatRoomBackendFlexisipChat);
linphone_chat_room_params_enable_group(params, TRUE);
LinphoneChatRoom *marieCr =
linphone_core_create_chat_room_2(marie->lc, params, initialSubject, participantsAddresses);
BC_ASSERT_PTR_NOT_NULL(marieCr);
if (!marieCr) goto end;
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneConferenceStateCreated,
initialMarieStats.number_of_LinphoneConferenceStateCreated + 1,
liblinphone_tester_sip_timeout));
const LinphoneAddress *localAddr = linphone_chat_room_get_local_address(marieCr);
BC_ASSERT_TRUE(linphone_address_weak_equal(localAddr, marieAddr));
confAddr = linphone_address_clone(linphone_chat_room_get_conference_address(marieCr));
// now with simulate foregound/backgroud switch to get a remote event handler list instead of a simple remote
// event handler
linphone_core_enter_background(marie->lc);
linphone_config_set_bool(linphone_core_get_config(marie->lc), "misc", "conference_event_package_force_full_state",
TRUE);
wait_for_list(coresList, &dummy, 1, 1000);
// Restart Marie
char *uuid = NULL;
if (linphone_config_get_string(linphone_core_get_config(marie->lc), "misc", "uuid", NULL)) {
uuid = bctbx_strdup(linphone_config_get_string(linphone_core_get_config(marie->lc), "misc", "uuid", NULL));
}
initialMarieStats = marie->stat;
coresList = bctbx_list_remove(coresList, marie->lc);
linphone_core_manager_reinit(marie);
bctbx_list_t *tmpCoresManagerList = bctbx_list_append(NULL, marie);
bctbx_list_free(init_core_for_conference(tmpCoresManagerList));
bctbx_list_free(tmpCoresManagerList);
// Make sure gruu is preserved
linphone_config_set_string(linphone_core_get_config(marie->lc), "misc", "uuid", uuid);
981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050
linphone_core_manager_start(marie, TRUE);
coresList = bctbx_list_append(coresList, marie->lc);
if (uuid) {
bctbx_free(uuid);
}
char *marieDeviceIdentity = linphone_core_get_device_identity(marie->lc);
LinphoneAddress *marieLocalAddr = linphone_address_new(marieDeviceIdentity);
bctbx_free(marieDeviceIdentity);
marieCr = linphone_core_search_chat_room(marie->lc, NULL, marieLocalAddr, confAddr, NULL);
linphone_address_unref(marieLocalAddr);
BC_ASSERT_PTR_NOT_NULL(marieCr);
// Clean db from chat room
if (marieCr) {
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
}
// Check that the chat room is correctly created on Pauline's side and that the participants are added
LinphoneChatRoom *paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats,
confAddr, initialSubject, 2, FALSE);
BC_ASSERT_PTR_NOT_NULL(paulineCr);
// Check that the chat room is correctly created on Laure's side and that the participants are added
LinphoneChatRoom *laureCr =
check_creation_chat_room_client_side(coresList, laure, &initialLaureStats, confAddr, initialSubject, 2, FALSE);
BC_ASSERT_PTR_NOT_NULL(laureCr);
end:
if (marieAddr) linphone_address_unref(marieAddr);
if (confAddr) linphone_address_unref(confAddr);
linphone_chat_room_params_unref(params);
bctbx_list_free_with_data(participantsAddresses, (bctbx_list_free_func)linphone_address_unref);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
linphone_core_manager_destroy(laure);
}
static void group_chat_room_creation_with_given_identity(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_dual_proxy_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
stats initialMarieStats = marie->stat;
BC_ASSERT_EQUAL((int)bctbx_list_size(linphone_core_get_proxy_config_list(marie->lc)), 2, int, "%d");
LinphoneProxyConfig *proxy = linphone_core_get_default_proxy_config(marie->lc);
LinphoneProxyConfig *secondProxy = linphone_core_get_proxy_config_list(marie->lc)->next->data;
LinphoneAddress *marieAddr = linphone_address_new(linphone_proxy_config_get_identity(proxy));
LinphoneAddress *marieSecondAddr = linphone_address_new(linphone_proxy_config_get_identity(secondProxy));
LinphoneChatRoomParams *params = linphone_core_create_default_chat_room_params(marie->lc);
LinphoneChatRoom *marieCr =
linphone_core_create_chat_room(marie->lc, params, marieAddr, "first chat room", participantsAddresses);
BC_ASSERT_PTR_NOT_NULL(marieCr);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneConferenceStateCreated,
1051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120
initialMarieStats.number_of_LinphoneConferenceStateCreated + 1,
liblinphone_tester_sip_timeout));
const LinphoneAddress *localAddr = linphone_chat_room_get_local_address(marieCr);
BC_ASSERT_TRUE(linphone_address_weak_equal(localAddr, marieAddr));
LinphoneChatRoom *secondMarieCr =
linphone_core_create_chat_room(marie->lc, params, marieSecondAddr, "second chat room", participantsAddresses);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneConferenceStateCreated,
initialMarieStats.number_of_LinphoneConferenceStateCreated + 1,
liblinphone_tester_sip_timeout));
localAddr = linphone_chat_room_get_local_address(secondMarieCr);
BC_ASSERT_TRUE(linphone_address_weak_equal(localAddr, marieSecondAddr));
// Clean db from chat room
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
linphone_core_manager_delete_chat_room(marie, secondMarieCr, coresList);
if (marieCr) linphone_chat_room_unref(marieCr);
if (secondMarieCr) linphone_chat_room_unref(secondMarieCr);
bctbx_list_free_with_data(participantsAddresses, (bctbx_list_free_func)linphone_address_unref);
linphone_address_unref(marieAddr);
linphone_address_unref(marieSecondAddr);
linphone_chat_room_params_unref(params);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
}
static void group_chat_room_creation_server(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *laure = linphone_core_manager_create("laure_tcp_rc");
LinphoneCoreManager *chloe = linphone_core_manager_create("chloe_rc");
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
int dummy = 0;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
coresManagerList = bctbx_list_append(coresManagerList, laure);
coresManagerList = bctbx_list_append(coresManagerList, chloe);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(laure->lc)));
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
stats initialLaureStats = laure->stat;
stats initialChloeStats = chloe->stat;
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
LinphoneChatRoom *marieCr =
create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject, FALSE,
LinphoneChatRoomEphemeralModeDeviceManaged);
const LinphoneAddress *confAddr = linphone_chat_room_get_conference_address(marieCr);
// Check that the chat room is correctly created on Pauline's side and that the participants are added
LinphoneChatRoom *paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats,
confAddr, initialSubject, 2, FALSE);
// Check that the chat room is correctly created on Laure's side and that the participants are added
LinphoneChatRoom *laureCr =
1121112211231124112511261127112811291130113111321133113411351136113711381139114011411142114311441145114611471148114911501151115211531154115511561157115811591160116111621163116411651166116711681169117011711172117311741175117611771178117911801181118211831184118511861187118811891190
check_creation_chat_room_client_side(coresList, laure, &initialLaureStats, confAddr, initialSubject, 2, FALSE);
// Pauline tries to change the subject but is not admin so it fails
const char *newSubject = "Let's go drink a beer";
linphone_chat_room_set_subject(paulineCr, newSubject);
wait_for_list(coresList, &dummy, 1, 1000);
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(marieCr), initialSubject);
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(paulineCr), initialSubject);
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(laureCr), initialSubject);
// Marie now changes the subject
linphone_chat_room_set_subject(marieCr, newSubject);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_subject_changed,
initialMarieStats.number_of_subject_changed + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_subject_changed,
initialPaulineStats.number_of_subject_changed + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_subject_changed,
initialLaureStats.number_of_subject_changed + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(marieCr), newSubject);
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(paulineCr), newSubject);
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(laureCr), newSubject);
// Marie designates Pauline as admin
LinphoneAddress *paulineAddr = linphone_address_new(linphone_core_get_identity(pauline->lc));
LinphoneParticipant *paulineParticipant = linphone_chat_room_find_participant(marieCr, paulineAddr);
linphone_address_unref(paulineAddr);
BC_ASSERT_PTR_NOT_NULL(paulineParticipant);
paulineParticipant = linphone_participant_ref(paulineParticipant);
linphone_chat_room_set_participant_admin_status(marieCr, paulineParticipant, TRUE);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_participant_admin_statuses_changed,
initialMarieStats.number_of_participant_admin_statuses_changed + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_participant_admin_statuses_changed,
initialPaulineStats.number_of_participant_admin_statuses_changed + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_participant_admin_statuses_changed,
initialLaureStats.number_of_participant_admin_statuses_changed + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(linphone_participant_is_admin(paulineParticipant));
linphone_participant_unref(paulineParticipant);
// Pauline adds Chloe to the chat room
participantsAddresses = NULL;
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(chloe->lc)));
linphone_chat_room_add_participants(paulineCr, participantsAddresses);
bctbx_list_free_with_data(participantsAddresses, (bctbx_list_free_func)linphone_address_unref);
participantsAddresses = NULL;
// Check that the chat room is correctly created on Chloe's side and that she was added everywhere
LinphoneChatRoom *chloeCr =
check_creation_chat_room_client_side(coresList, chloe, &initialChloeStats, confAddr, newSubject, 3, FALSE);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_participants_added,
initialMarieStats.number_of_participants_added + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_participants_added,
initialPaulineStats.number_of_participants_added + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_participants_added,
initialLaureStats.number_of_participants_added + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(marieCr), 3, int, "%d");
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(paulineCr), 3, int, "%d");
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(laureCr), 3, int, "%d");
// Pauline revokes the admin status of Marie
LinphoneAddress *marieAddr = linphone_address_new(linphone_core_get_identity(marie->lc));
LinphoneParticipant *marieParticipant = linphone_chat_room_find_participant(paulineCr, marieAddr);
linphone_address_unref(marieAddr);
BC_ASSERT_PTR_NOT_NULL(marieParticipant);
marieParticipant = linphone_participant_ref(marieParticipant);
linphone_chat_room_set_participant_admin_status(paulineCr, marieParticipant, FALSE);
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_participant_admin_statuses_changed,
1191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260
initialPaulineStats.number_of_participant_admin_statuses_changed + 2,
liblinphone_tester_sip_timeout));
BC_ASSERT_FALSE(linphone_participant_is_admin(marieParticipant));
// Marie tries to change the subject again but is not admin, so it is not changed
linphone_chat_room_set_subject(marieCr, initialSubject);
wait_for_list(coresList, &dummy, 1, 1000);
// Chloe begins composing a message
BC_ASSERT_PTR_NOT_NULL(chloeCr);
linphone_chat_room_compose(chloeCr);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneIsComposingActiveReceived,
initialMarieStats.number_of_LinphoneIsComposingActiveReceived + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneIsComposingActiveReceived,
initialPaulineStats.number_of_LinphoneIsComposingActiveReceived + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_LinphoneIsComposingActiveReceived,
initialLaureStats.number_of_LinphoneIsComposingActiveReceived + 1,
liblinphone_tester_sip_timeout));
const char *chloeTextMessage = "Hello";
LinphoneChatMessage *chloeMessage = _send_message(chloeCr, chloeTextMessage);
BC_ASSERT_TRUE(wait_for_list(coresList, &chloe->stat.number_of_LinphoneMessageDelivered,
initialChloeStats.number_of_LinphoneMessageDelivered + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneMessageReceived,
initialMarieStats.number_of_LinphoneMessageReceived + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageReceived,
initialPaulineStats.number_of_LinphoneMessageReceived + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_LinphoneMessageReceived,
initialLaureStats.number_of_LinphoneMessageReceived + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneIsComposingIdleReceived,
initialMarieStats.number_of_LinphoneIsComposingIdleReceived + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneIsComposingIdleReceived,
initialPaulineStats.number_of_LinphoneIsComposingIdleReceived + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_LinphoneIsComposingIdleReceived,
initialLaureStats.number_of_LinphoneIsComposingIdleReceived + 1,
liblinphone_tester_sip_timeout));
LinphoneAddress *chloeAddr;
if (BC_ASSERT_PTR_NOT_NULL(marie->stat.last_received_chat_message)) {
BC_ASSERT_STRING_EQUAL(linphone_chat_message_get_text(marie->stat.last_received_chat_message),
chloeTextMessage);
linphone_chat_message_unref(chloeMessage);
chloeAddr = linphone_address_new(linphone_core_get_identity(chloe->lc));
BC_ASSERT_TRUE(linphone_address_weak_equal(
chloeAddr, linphone_chat_message_get_from_address(marie->stat.last_received_chat_message)));
linphone_address_unref(chloeAddr);
}
// Pauline removes Laure from the chat room
LinphoneAddress *laureAddr = linphone_address_new(linphone_core_get_identity(laure->lc));
LinphoneParticipant *laureParticipant = linphone_chat_room_find_participant(paulineCr, laureAddr);
linphone_address_unref(laureAddr);
BC_ASSERT_PTR_NOT_NULL(laureParticipant);
laureParticipant = linphone_participant_ref(laureParticipant);
linphone_chat_room_remove_participant(paulineCr, laureParticipant);
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(marieCr), newSubject);
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_LinphoneConferenceStateTerminated,
initialLaureStats.number_of_LinphoneConferenceStateTerminated + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &chloe->stat.number_of_participants_removed,
initialChloeStats.number_of_participants_removed + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_participants_removed,
initialMarieStats.number_of_participants_removed + 1, liblinphone_tester_sip_timeout));
1261126212631264126512661267126812691270127112721273127412751276127712781279128012811282128312841285128612871288128912901291129212931294129512961297129812991300130113021303130413051306130713081309131013111312131313141315131613171318131913201321132213231324132513261327132813291330
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_participants_removed,
initialPaulineStats.number_of_participants_removed + 1,
liblinphone_tester_sip_timeout));
linphone_participant_unref(laureParticipant);
// Pauline removes Marie and Chloe from the chat room
marieAddr = linphone_address_new(linphone_core_get_identity(marie->lc));
marieParticipant = linphone_chat_room_find_participant(paulineCr, marieAddr);
linphone_address_unref(marieAddr);
BC_ASSERT_PTR_NOT_NULL(marieParticipant);
chloeAddr = linphone_address_new(linphone_core_get_identity(chloe->lc));
LinphoneParticipant *chloeParticipant = linphone_chat_room_find_participant(paulineCr, chloeAddr);
linphone_address_unref(chloeAddr);
BC_ASSERT_PTR_NOT_NULL(chloeParticipant);
chloeParticipant = linphone_participant_ref(chloeParticipant);
bctbx_list_t *participantsToRemove = NULL;
initialPaulineStats = pauline->stat;
participantsToRemove = bctbx_list_append(participantsToRemove, marieParticipant);
participantsToRemove = bctbx_list_append(participantsToRemove, chloeParticipant);
linphone_chat_room_remove_participants(paulineCr, participantsToRemove);
bctbx_list_free_with_data(participantsToRemove, (bctbx_list_free_func)linphone_participant_unref);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneConferenceStateTerminated,
initialMarieStats.number_of_LinphoneConferenceStateTerminated + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &chloe->stat.number_of_LinphoneConferenceStateTerminated,
initialChloeStats.number_of_LinphoneConferenceStateTerminated + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_participants_removed,
initialPaulineStats.number_of_participants_removed + 2,
liblinphone_tester_sip_timeout));
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(paulineCr), 0, int, "%d");
// Pauline leaves the chat room
wait_for_list(coresList, &dummy, 1, 1000);
linphone_chat_room_leave(paulineCr);
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneConferenceStateTerminationPending,
initialPaulineStats.number_of_LinphoneConferenceStateTerminationPending + 1, 100));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneConferenceStateTerminated,
initialPaulineStats.number_of_LinphoneConferenceStateTerminated + 1,
liblinphone_tester_sip_timeout));
// Clean db from chat room
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
linphone_core_manager_delete_chat_room(laure, laureCr, coresList);
linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
linphone_core_manager_delete_chat_room(chloe, chloeCr, coresList);
BC_ASSERT_EQUAL(linphone_core_get_call_history_size(marie->lc), 0, int, "%i");
BC_ASSERT_EQUAL(linphone_core_get_call_history_size(laure->lc), 0, int, "%i");
BC_ASSERT_EQUAL(linphone_core_get_call_history_size(pauline->lc), 0, int, "%i");
BC_ASSERT_EQUAL(linphone_core_get_call_history_size(chloe->lc), 0, int, "%i");
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
linphone_core_manager_destroy(laure);
linphone_core_manager_destroy(chloe);
}
static void group_chat_room_creation_server_network_down(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
1331133213331334133513361337133813391340134113421343134413451346134713481349135013511352135313541355135613571358135913601361136213631364136513661367136813691370137113721373137413751376137713781379138013811382138313841385138613871388138913901391139213931394139513961397139813991400
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
LinphoneChatRoomParams *params = linphone_core_create_default_chat_room_params(marie->lc);
linphone_chat_room_params_set_backend(params, LinphoneChatRoomBackendFlexisipChat);
linphone_chat_room_params_enable_group(params, TRUE);
linphone_chat_room_params_enable_encryption(params, FALSE);
LinphoneChatRoom *marieCr =
linphone_core_create_chat_room_2(marie->lc, params, initialSubject, participantsAddresses);
linphone_chat_room_params_unref(params);
BC_ASSERT_TRUE(
wait_for_until(marie->lc, pauline->lc, &(marie->stat.number_of_LinphoneConferenceStateInstantiated), 1, 100));
// Check that the chat room is correctly created on Marie's side and that the participants are added
BC_ASSERT_TRUE(wait_for_until(marie->lc, pauline->lc,
&(marie->stat.number_of_LinphoneConferenceStateCreationPending), 1,
liblinphone_tester_sip_timeout));
linphone_core_set_network_reachable(marie->lc, FALSE);
BC_ASSERT_TRUE(wait_for_until(marie->lc, pauline->lc,
&(marie->stat.number_of_LinphoneConferenceStateCreationFailed), 1,
2 * liblinphone_tester_sip_timeout));
bctbx_list_free_with_data(participantsAddresses, (bctbx_list_free_func)linphone_address_unref);
participantsAddresses = NULL;
// Clean db from chat room
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
if (marieCr) linphone_chat_room_unref(marieCr);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
}
static void group_chat_room_creation_server_network_down_up(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
int dummy = 0;
stats initialPaulineStats = pauline->stat;
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
LinphoneChatRoomParams *params = linphone_core_create_default_chat_room_params(marie->lc);
linphone_chat_room_params_set_backend(params, LinphoneChatRoomBackendFlexisipChat);
linphone_chat_room_params_enable_group(params, TRUE);
linphone_chat_room_params_enable_encryption(params, FALSE);
LinphoneChatRoom *marieCr =
linphone_core_create_chat_room_2(marie->lc, params, initialSubject, participantsAddresses);
linphone_chat_room_params_unref(params);
BC_ASSERT_TRUE(
wait_for_until(marie->lc, pauline->lc, &(marie->stat.number_of_LinphoneConferenceStateInstantiated), 1, 100));
// Check that the chat room is correctly created on Marie's side and that the participants are added
BC_ASSERT_TRUE(wait_for_until(marie->lc, pauline->lc,
1401140214031404140514061407140814091410141114121413141414151416141714181419142014211422142314241425142614271428142914301431143214331434143514361437143814391440144114421443144414451446144714481449145014511452145314541455145614571458145914601461146214631464146514661467146814691470
&(marie->stat.number_of_LinphoneConferenceStateCreationPending), 1,
liblinphone_tester_sip_timeout));
linphone_core_set_network_reachable(marie->lc, FALSE);
BC_ASSERT_FALSE(wait_for_until(marie->lc, pauline->lc, &dummy, 1, 5000));
linphone_core_set_network_reachable(marie->lc, TRUE);
BC_ASSERT_TRUE(wait_for_until(marie->lc, pauline->lc, &(marie->stat.number_of_LinphoneConferenceStateCreated), 1,
2 * liblinphone_tester_sip_timeout));
const LinphoneAddress *confAddr = linphone_chat_room_get_conference_address(marieCr);
LinphoneChatRoom *paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats,
confAddr, initialSubject, 1, FALSE);
BC_ASSERT_PTR_NOT_NULL(paulineCr);
bctbx_list_free_with_data(participantsAddresses, (bctbx_list_free_func)linphone_address_unref);
participantsAddresses = NULL;
// Clean db from chat room
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
if (marieCr) linphone_chat_room_unref(marieCr);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
}
static void group_chat_room_add_participant(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *laure = linphone_core_manager_create("laure_tcp_rc");
LinphoneCoreManager *chloe = linphone_core_manager_create("chloe_rc");
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
coresManagerList = bctbx_list_append(coresManagerList, laure);
coresManagerList = bctbx_list_append(coresManagerList, chloe);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
linphone_core_remove_linphone_spec(chloe->lc, "groupchat");
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(marie->lc)));
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(laure->lc)));
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
stats initialLaureStats = laure->stat;
stats initialChloeStats = chloe->stat;
// Pauline creates a new group chat room
const char *initialSubject = "Colleagues";
LinphoneChatRoom *paulineCr =
create_chat_room_client_side(coresList, pauline, &initialPaulineStats, participantsAddresses, initialSubject,
FALSE, LinphoneChatRoomEphemeralModeDeviceManaged);
LinphoneAddress *confAddr = linphone_address_clone(linphone_chat_room_get_conference_address(paulineCr));
// Check that the chat room is correctly created on Pauline's side and that the participants are added
LinphoneChatRoom *marieCr =
check_creation_chat_room_client_side(coresList, marie, &initialMarieStats, confAddr, initialSubject, 2, FALSE);
// Check that the chat room is correctly created on Laure's side and that the participants are added
LinphoneChatRoom *laureCr =
check_creation_chat_room_client_side(coresList, laure, &initialLaureStats, confAddr, initialSubject, 2, FALSE);
// To simulate dialog removal for Pauline
linphone_core_set_network_reachable(pauline->lc, FALSE);
1471147214731474147514761477147814791480148114821483148414851486148714881489149014911492149314941495149614971498149915001501150215031504150515061507150815091510151115121513151415151516151715181519152015211522152315241525152615271528152915301531153215331534153515361537153815391540
LinphoneAddress *paulineAddr = linphone_address_clone(linphone_chat_room_get_peer_address(paulineCr));
coresList = bctbx_list_remove(coresList, pauline->lc);
linphone_core_manager_reinit(pauline);
bctbx_list_t *tmpCoresManagerList = bctbx_list_append(NULL, pauline);
bctbx_list_t *tmpCoresList = init_core_for_conference(tmpCoresManagerList);
bctbx_list_free(tmpCoresManagerList);
coresList = bctbx_list_concat(coresList, tmpCoresList);
linphone_core_manager_start(pauline, TRUE);
paulineCr = linphone_core_search_chat_room(pauline->lc, NULL, NULL, paulineAddr, NULL);
BC_ASSERT_PTR_NOT_NULL(paulineCr);
linphone_address_unref(paulineAddr);
// Pauline adds Chloe to the chat room
participantsAddresses = NULL;
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(chloe->lc)));
if (paulineCr) {
linphone_chat_room_add_participants(paulineCr, participantsAddresses);
}
bctbx_list_free_with_data(participantsAddresses, (bctbx_list_free_func)linphone_address_unref);
participantsAddresses = NULL;
// Refused by server because group chat disabled for Chloe
BC_ASSERT_FALSE(wait_for_list(coresList, &marie->stat.number_of_participants_added,
initialMarieStats.number_of_participants_added + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_FALSE(wait_for_list(coresList, &pauline->stat.number_of_participants_added,
initialPaulineStats.number_of_participants_added + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_FALSE(wait_for_list(coresList, &laure->stat.number_of_participants_added,
initialLaureStats.number_of_participants_added + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(marieCr), 2, int, "%d");
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(paulineCr), 2, int, "%d");
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(laureCr), 2, int, "%d");
// Try to search for a participant that is not in the chatroom
LinphoneAddress *fakeAddr = linphone_address_new("sip:toto@sip.example.org");
LinphoneParticipant *fakeParticipant = linphone_chat_room_find_participant(marieCr, fakeAddr);
linphone_address_unref(fakeAddr);
BC_ASSERT_PTR_NULL(fakeParticipant);
// Pauline begins composing a message
linphone_chat_room_compose(paulineCr);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneIsComposingActiveReceived,
initialMarieStats.number_of_LinphoneIsComposingActiveReceived + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_LinphoneIsComposingActiveReceived,
initialPaulineStats.number_of_LinphoneIsComposingActiveReceived + 1,
liblinphone_tester_sip_timeout));
// Now, Chloe is upgrading to group chat client
linphone_core_set_network_reachable(chloe->lc, FALSE);
coresList = bctbx_list_remove(coresList, chloe->lc);
linphone_core_manager_reinit(chloe);
tmpCoresManagerList = bctbx_list_append(NULL, chloe);
tmpCoresList = init_core_for_conference(tmpCoresManagerList);
bctbx_list_free(tmpCoresManagerList);
coresList = bctbx_list_concat(coresList, tmpCoresList);
linphone_core_manager_start(chloe, TRUE);
// Pauline adds Chloe to the chat room
participantsAddresses = NULL;
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(chloe->lc)));
linphone_chat_room_add_participants(paulineCr, participantsAddresses);
bctbx_list_free_with_data(participantsAddresses, (bctbx_list_free_func)linphone_address_unref);
participantsAddresses = NULL;
// Check that the chat room is correctly created on Chloe's side and that she was added everywhere
LinphoneChatRoom *chloeCr =
check_creation_chat_room_client_side(coresList, chloe, &initialChloeStats, confAddr, initialSubject, 3, FALSE);
1541154215431544154515461547154815491550155115521553155415551556155715581559156015611562156315641565156615671568156915701571157215731574157515761577157815791580158115821583158415851586158715881589159015911592159315941595159615971598159916001601160216031604160516061607160816091610
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_participants_added,
initialMarieStats.number_of_participants_added + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_participants_added,
initialPaulineStats.number_of_participants_added + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_participants_added,
initialLaureStats.number_of_participants_added + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(marieCr), 3, int, "%d");
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(paulineCr), 3, int, "%d");
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(laureCr), 3, int, "%d");
// Clean db from chat room
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
linphone_core_manager_delete_chat_room(laure, laureCr, coresList);
linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
linphone_core_manager_delete_chat_room(chloe, chloeCr, coresList);
BC_ASSERT_EQUAL(linphone_core_get_call_history_size(marie->lc), 0, int, "%i");
BC_ASSERT_EQUAL(linphone_core_get_call_history_size(laure->lc), 0, int, "%i");
BC_ASSERT_EQUAL(linphone_core_get_call_history_size(pauline->lc), 0, int, "%i");
BC_ASSERT_EQUAL(linphone_core_get_call_history_size(chloe->lc), 0, int, "%i");
linphone_address_unref(confAddr);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
linphone_core_manager_destroy(laure);
linphone_core_manager_destroy(chloe);
}
static int im_encryption_engine_process_incoming_message_cb(BCTBX_UNUSED(LinphoneImEncryptionEngine *engine),
BCTBX_UNUSED(LinphoneChatRoom *room),
LinphoneChatMessage *msg) {
if (linphone_chat_message_get_content_type(msg)) {
if (strcmp(linphone_chat_message_get_content_type(msg), "cipher/b64") == 0) {
size_t b64Size = 0;
unsigned char *output;
const char *msg_str = linphone_chat_message_get_text(msg);
bctbx_base64_decode(NULL, &b64Size, (unsigned char *)msg_str, strlen(msg_str));
output = (unsigned char *)ms_malloc(b64Size + 1),
bctbx_base64_decode(output, &b64Size, (unsigned char *)msg_str, strlen(msg_str));
output[b64Size] = '\0';
linphone_chat_message_set_text(msg, (char *)output);
ms_free(output);
linphone_chat_message_set_content_type(msg, "message/cpim");
return 0;
} else if (strcmp(linphone_chat_message_get_content_type(msg), "application/im-iscomposing+xml") == 0) {
return -1; // Not encrypted, nothing to do
} else {
return 488; // Not acceptable
}
}
return 500;
}
static int im_encryption_engine_process_outgoing_message_cb(BCTBX_UNUSED(LinphoneImEncryptionEngine *engine),
BCTBX_UNUSED(LinphoneChatRoom *room),
LinphoneChatMessage *msg) {
if (strcmp(linphone_chat_message_get_content_type(msg), "message/cpim") == 0) {
size_t b64Size = 0;
unsigned char *output;
const char *msg_str = linphone_chat_message_get_text(msg);
bctbx_base64_encode(NULL, &b64Size, (unsigned char *)msg_str, strlen(msg_str));
output = (unsigned char *)ms_malloc0(b64Size + 1);
bctbx_base64_encode(output, &b64Size, (unsigned char *)msg_str, strlen(msg_str));
output[b64Size] = '\0';
linphone_chat_message_set_text(msg, (const char *)output);
ms_free(output);
linphone_chat_message_set_content_type(msg, "cipher/b64");
return 0;
1611161216131614161516161617161816191620162116221623162416251626162716281629163016311632163316341635163616371638163916401641164216431644164516461647164816491650165116521653165416551656165716581659166016611662166316641665166616671668166916701671167216731674167516761677167816791680
}
return -1;
}
static void group_chat_room_message(bool_t encrypt, bool_t sal_error) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *chloe = linphone_core_manager_create("chloe_rc");
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
coresManagerList = bctbx_list_append(coresManagerList, chloe);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(chloe->lc)));
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
stats initialChloeStats = chloe->stat;
LinphoneImEncryptionEngine *marie_imee = linphone_im_encryption_engine_new();
LinphoneImEncryptionEngineCbs *marie_cbs = linphone_im_encryption_engine_get_callbacks(marie_imee);
LinphoneImEncryptionEngine *pauline_imee = linphone_im_encryption_engine_new();
LinphoneImEncryptionEngineCbs *pauline_cbs = linphone_im_encryption_engine_get_callbacks(pauline_imee);
LinphoneImEncryptionEngine *chloe_imee = linphone_im_encryption_engine_new();
LinphoneImEncryptionEngineCbs *chloe_cbs = linphone_im_encryption_engine_get_callbacks(chloe_imee);
if (encrypt) {
linphone_im_encryption_engine_cbs_set_process_outgoing_message(
marie_cbs, im_encryption_engine_process_outgoing_message_cb);
linphone_im_encryption_engine_cbs_set_process_outgoing_message(
pauline_cbs, im_encryption_engine_process_outgoing_message_cb);
linphone_im_encryption_engine_cbs_set_process_outgoing_message(
chloe_cbs, im_encryption_engine_process_outgoing_message_cb);
linphone_im_encryption_engine_cbs_set_process_incoming_message(
marie_cbs, im_encryption_engine_process_incoming_message_cb);
linphone_im_encryption_engine_cbs_set_process_incoming_message(
pauline_cbs, im_encryption_engine_process_incoming_message_cb);
linphone_im_encryption_engine_cbs_set_process_incoming_message(
chloe_cbs, im_encryption_engine_process_incoming_message_cb);
linphone_core_set_im_encryption_engine(marie->lc, marie_imee);
linphone_core_set_im_encryption_engine(pauline->lc, pauline_imee);
linphone_core_set_im_encryption_engine(chloe->lc, chloe_imee);
}
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
LinphoneChatRoom *marieCr =
create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject, FALSE,
LinphoneChatRoomEphemeralModeDeviceManaged);
const LinphoneAddress *confAddr = linphone_chat_room_get_conference_address(marieCr);
// Check that the chat room is correctly created on Pauline's side and that the participants are added
LinphoneChatRoom *paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats,
confAddr, initialSubject, 2, FALSE);
// Check that the chat room is correctly created on Chloe's side and that the participants are added
LinphoneChatRoom *chloeCr =
check_creation_chat_room_client_side(coresList, chloe, &initialChloeStats, confAddr, initialSubject, 2, FALSE);
// Chloe begins composing a message
linphone_chat_room_compose(chloeCr);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneIsComposingActiveReceived,
initialMarieStats.number_of_LinphoneIsComposingActiveReceived + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneIsComposingActiveReceived,
1681168216831684168516861687168816891690169116921693169416951696169716981699170017011702170317041705170617071708170917101711171217131714171517161717171817191720172117221723172417251726172717281729173017311732173317341735173617371738173917401741174217431744174517461747174817491750
initialPaulineStats.number_of_LinphoneIsComposingActiveReceived + 1,
liblinphone_tester_sip_timeout));
const char *chloeTextMessage = "Hello";
LinphoneChatMessage *chloeMessage = _send_message(chloeCr, chloeTextMessage);
const char *messageId = linphone_chat_message_get_message_id(chloeMessage);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneMessageReceived,
initialMarieStats.number_of_LinphoneMessageReceived + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageReceived,
initialPaulineStats.number_of_LinphoneMessageReceived + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneIsComposingIdleReceived,
initialMarieStats.number_of_LinphoneIsComposingIdleReceived + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneIsComposingIdleReceived,
initialPaulineStats.number_of_LinphoneIsComposingIdleReceived + 1,
liblinphone_tester_sip_timeout));
LinphoneChatMessage *marieLastMsg = marie->stat.last_received_chat_message;
if (!BC_ASSERT_PTR_NOT_NULL(marieLastMsg)) goto end;
BC_ASSERT_STRING_EQUAL(linphone_chat_message_get_text(marieLastMsg), chloeTextMessage);
LinphoneChatMessage *foundMessage = linphone_chat_room_find_message(chloeCr, messageId);
linphone_chat_message_unref(chloeMessage); // Unref here because of messageId using
BC_ASSERT_PTR_NOT_NULL(foundMessage);
BC_ASSERT_PTR_NOT_NULL(linphone_chat_message_get_text(foundMessage));
linphone_chat_message_unref(foundMessage);
LinphoneAddress *chloeAddr = linphone_address_new(linphone_core_get_identity(chloe->lc));
BC_ASSERT_TRUE(linphone_address_weak_equal(chloeAddr, linphone_chat_message_get_from_address(marieLastMsg)));
linphone_address_unref(chloeAddr);
// Pauline begins composing a messagewith some accents
linphone_chat_room_compose(paulineCr);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneIsComposingActiveReceived,
initialMarieStats.number_of_LinphoneIsComposingActiveReceived + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &chloe->stat.number_of_LinphoneIsComposingActiveReceived,
initialChloeStats.number_of_LinphoneIsComposingActiveReceived + 1,
liblinphone_tester_sip_timeout));
const char *paulineTextMessage = "Héllö Dàrling";
LinphoneChatMessage *paulineMessage = _send_message(paulineCr, paulineTextMessage);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneMessageReceived,
initialMarieStats.number_of_LinphoneMessageReceived + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &chloe->stat.number_of_LinphoneMessageReceived,
initialChloeStats.number_of_LinphoneMessageReceived + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneIsComposingIdleReceived,
initialMarieStats.number_of_LinphoneIsComposingIdleReceived + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &chloe->stat.number_of_LinphoneIsComposingIdleReceived,
initialChloeStats.number_of_LinphoneIsComposingIdleReceived + 1,
liblinphone_tester_sip_timeout));
marieLastMsg = marie->stat.last_received_chat_message;
if (!BC_ASSERT_PTR_NOT_NULL(marieLastMsg)) goto end;
BC_ASSERT_STRING_EQUAL(linphone_chat_message_get_utf8_text(marieLastMsg), paulineTextMessage);
linphone_chat_message_unref(paulineMessage);
LinphoneAddress *paulineAddr = linphone_address_new(linphone_core_get_identity(pauline->lc));
BC_ASSERT_TRUE(linphone_address_weak_equal(paulineAddr, linphone_chat_message_get_from_address(marieLastMsg)));
linphone_address_unref(paulineAddr);
if (sal_error) {
sal_set_send_error(linphone_core_get_sal(marie->lc), -1);
LinphoneChatMessage *msg = _send_message(marieCr, "Bli bli bli");
char *message_id = ms_strdup(linphone_chat_message_get_message_id(msg));
BC_ASSERT_STRING_NOT_EQUAL(message_id, "");
1751175217531754175517561757175817591760176117621763176417651766176717681769177017711772177317741775177617771778177917801781178217831784178517861787178817891790179117921793179417951796179717981799180018011802180318041805180618071808180918101811181218131814181518161817181818191820
wait_for_list(coresList, NULL, 0, 1000);
sal_set_send_error(linphone_core_get_sal(marie->lc), 0);
linphone_chat_message_send(msg);
const char *message_id_2 = linphone_chat_message_get_message_id(msg);
BC_ASSERT_STRING_NOT_EQUAL(message_id_2, "");
BC_ASSERT_STRING_EQUAL(message_id, message_id_2);
ms_free(message_id);
wait_for_list(coresList, NULL, 0, 1000);
linphone_core_refresh_registers(marie->lc);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneRegistrationOk,
initialMarieStats.number_of_LinphoneRegistrationOk + 1,
liblinphone_tester_sip_timeout));
linphone_chat_message_unref(msg);
}
end:
// Clean db from chat room
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
linphone_core_manager_delete_chat_room(chloe, chloeCr, coresList);
linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
linphone_im_encryption_engine_unref(marie_imee);
linphone_im_encryption_engine_unref(pauline_imee);
linphone_im_encryption_engine_unref(chloe_imee);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
linphone_core_manager_destroy(chloe);
}
static void group_chat_room_send_message(void) {
group_chat_room_message(FALSE, FALSE);
}
static void group_chat_room_send_message_encrypted(void) {
group_chat_room_message(TRUE, FALSE);
}
static void group_chat_room_send_message_with_error(void) {
group_chat_room_message(FALSE, TRUE);
}
static void group_chat_room_invite_multi_register_account(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline1 = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *pauline2 = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *laure = linphone_core_manager_create("laure_tcp_rc");
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline1);
coresManagerList = bctbx_list_append(coresManagerList, pauline2);
coresManagerList = bctbx_list_append(coresManagerList, laure);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline1->lc)));
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(laure->lc)));
stats initialMarieStats = marie->stat;
stats initialPauline1Stats = pauline1->stat;
stats initialPauline2Stats = pauline2->stat;
stats initialLaureStats = laure->stat;
// Marie creates a new group chat room
1821182218231824182518261827182818291830183118321833183418351836183718381839184018411842184318441845184618471848184918501851185218531854185518561857185818591860186118621863186418651866186718681869187018711872187318741875187618771878187918801881188218831884188518861887188818891890
const char *initialSubject = "Colleagues";
LinphoneChatRoom *marieCr =
create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject, FALSE,
LinphoneChatRoomEphemeralModeDeviceManaged);
const LinphoneAddress *confAddr = linphone_chat_room_get_conference_address(marieCr);
// Check that the chat room is correctly created on Pauline1's side and that the participants are added
LinphoneChatRoom *paulineCr = check_creation_chat_room_client_side(coresList, pauline1, &initialPauline1Stats,
confAddr, initialSubject, 2, FALSE);
// Check that the chat room is correctly created on Pauline2's side and that the participants are added
LinphoneChatRoom *paulineCr2 = check_creation_chat_room_client_side(coresList, pauline2, &initialPauline2Stats,
confAddr, initialSubject, 2, FALSE);
// Check that the chat room is correctly created on Laure's side and that the participants are added
LinphoneChatRoom *laureCr =
check_creation_chat_room_client_side(coresList, laure, &initialLaureStats, confAddr, initialSubject, 2, FALSE);
// Clean db from chat room
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
linphone_core_manager_delete_chat_room(laure, laureCr, coresList);
linphone_core_manager_delete_chat_room(pauline1, paulineCr, coresList);
linphone_core_delete_chat_room(pauline2->lc, paulineCr2);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline1);
linphone_core_manager_destroy(pauline2);
linphone_core_manager_destroy(laure);
}
static void group_chat_room_add_admin(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *laure = linphone_core_manager_create("laure_tcp_rc");
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
coresManagerList = bctbx_list_append(coresManagerList, laure);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(laure->lc)));
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
stats initialLaureStats = laure->stat;
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
LinphoneChatRoom *marieCr =
create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject, FALSE,
LinphoneChatRoomEphemeralModeDeviceManaged);
const LinphoneAddress *confAddr = linphone_chat_room_get_conference_address(marieCr);
// Check that the chat room is correctly created on Pauline's side and that the participants are added
LinphoneChatRoom *paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats,
confAddr, initialSubject, 2, FALSE);
// Check that the chat room is correctly created on Laure's side and that the participants are added
LinphoneChatRoom *laureCr =
check_creation_chat_room_client_side(coresList, laure, &initialLaureStats, confAddr, initialSubject, 2, FALSE);
if (!BC_ASSERT_PTR_NOT_NULL(marieCr) || !BC_ASSERT_PTR_NOT_NULL(paulineCr) || !BC_ASSERT_PTR_NOT_NULL(laureCr))
goto end;
// Marie designates Pauline as admin
1891189218931894189518961897189818991900190119021903190419051906190719081909191019111912191319141915191619171918191919201921192219231924192519261927192819291930193119321933193419351936193719381939194019411942194319441945194619471948194919501951195219531954195519561957195819591960
LinphoneAddress *paulineAddr = linphone_address_new(linphone_core_get_identity(pauline->lc));
LinphoneParticipant *paulineParticipant = linphone_chat_room_find_participant(marieCr, paulineAddr);
linphone_address_unref(paulineAddr);
BC_ASSERT_PTR_NOT_NULL(paulineParticipant);
linphone_chat_room_set_participant_admin_status(marieCr, paulineParticipant, TRUE);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_participant_admin_statuses_changed,
initialMarieStats.number_of_participant_admin_statuses_changed + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_participant_admin_statuses_changed,
initialPaulineStats.number_of_participant_admin_statuses_changed + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_participant_admin_statuses_changed,
initialLaureStats.number_of_participant_admin_statuses_changed + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(linphone_participant_is_admin(paulineParticipant));
end:
// Clean db from chat room
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
linphone_core_manager_delete_chat_room(laure, laureCr, coresList);
linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
linphone_core_manager_destroy(laure);
}
static void group_chat_room_add_admin_lately_notified(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *laure = linphone_core_manager_create("laure_tcp_rc");
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
coresManagerList = bctbx_list_append(coresManagerList, laure);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(laure->lc)));
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
stats initialLaureStats = laure->stat;
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
LinphoneChatRoom *marieCr =
create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject, FALSE,
LinphoneChatRoomEphemeralModeDeviceManaged);
const LinphoneAddress *confAddr = linphone_chat_room_get_conference_address(marieCr);
// Check that the chat room is correctly created on Pauline's side and that the participants are added
LinphoneChatRoom *paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats,
confAddr, initialSubject, 2, FALSE);
// Check that the chat room is correctly created on Laure's side and that the participants are added
LinphoneChatRoom *laureCr =
check_creation_chat_room_client_side(coresList, laure, &initialLaureStats, confAddr, initialSubject, 2, FALSE);
if (!BC_ASSERT_PTR_NOT_NULL(marieCr) || !BC_ASSERT_PTR_NOT_NULL(paulineCr) || !BC_ASSERT_PTR_NOT_NULL(laureCr))
goto end;
// Simulate pauline has disappeared
linphone_core_set_network_reachable(pauline->lc, FALSE);
// Marie designates Pauline as admin
LinphoneAddress *paulineAddr = linphone_address_new(linphone_core_get_identity(pauline->lc));
1961196219631964196519661967196819691970197119721973197419751976197719781979198019811982198319841985198619871988198919901991199219931994199519961997199819992000200120022003200420052006200720082009201020112012201320142015201620172018201920202021202220232024202520262027202820292030
LinphoneParticipant *paulineParticipant = linphone_chat_room_find_participant(marieCr, paulineAddr);
linphone_address_unref(paulineAddr);
BC_ASSERT_PTR_NOT_NULL(paulineParticipant);
linphone_chat_room_set_participant_admin_status(marieCr, paulineParticipant, TRUE);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_participant_admin_statuses_changed,
initialMarieStats.number_of_participant_admin_statuses_changed + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_participant_admin_statuses_changed,
initialLaureStats.number_of_participant_admin_statuses_changed + 1,
liblinphone_tester_sip_timeout));
// Make sure pauline is not notified
BC_ASSERT_FALSE(wait_for_list(coresList, &pauline->stat.number_of_participant_admin_statuses_changed,
initialPaulineStats.number_of_participant_admin_statuses_changed + 1, 3000));
linphone_core_set_network_reachable(pauline->lc, TRUE);
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_participant_admin_statuses_changed,
initialPaulineStats.number_of_participant_admin_statuses_changed + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(linphone_participant_is_admin(paulineParticipant));
end:
// Clean db from chat room
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
linphone_core_manager_delete_chat_room(laure, laureCr, coresList);
linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
linphone_core_manager_destroy(laure);
}
static void group_chat_room_add_admin_non_admin(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *laure = linphone_core_manager_create("laure_tcp_rc");
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
coresManagerList = bctbx_list_append(coresManagerList, laure);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(laure->lc)));
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
stats initialLaureStats = laure->stat;
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
LinphoneChatRoom *marieCr =
create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject, FALSE,
LinphoneChatRoomEphemeralModeDeviceManaged);
const LinphoneAddress *confAddr = linphone_chat_room_get_conference_address(marieCr);
// Check that the chat room is correctly created on Pauline's side and that the participants are added
LinphoneChatRoom *paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats,
confAddr, initialSubject, 2, FALSE);
// Check that the chat room is correctly created on Laure's side and that the participants are added
LinphoneChatRoom *laureCr =
check_creation_chat_room_client_side(coresList, laure, &initialLaureStats, confAddr, initialSubject, 2, FALSE);
if (!BC_ASSERT_PTR_NOT_NULL(marieCr) || !BC_ASSERT_PTR_NOT_NULL(paulineCr) || !BC_ASSERT_PTR_NOT_NULL(laureCr))
goto end;
2031203220332034203520362037203820392040204120422043204420452046204720482049205020512052205320542055205620572058205920602061206220632064206520662067206820692070207120722073207420752076207720782079208020812082208320842085208620872088208920902091209220932094209520962097209820992100
// Pauline designates Laure as admin
LinphoneAddress *laureAddr = linphone_address_new(linphone_core_get_identity(laure->lc));
LinphoneParticipant *laureParticipant = linphone_chat_room_find_participant(paulineCr, laureAddr);
linphone_address_unref(laureAddr);
BC_ASSERT_PTR_NOT_NULL(laureParticipant);
linphone_chat_room_set_participant_admin_status(paulineCr, laureParticipant, TRUE);
BC_ASSERT_FALSE(linphone_participant_is_admin(laureParticipant));
end:
// Clean db from chat room
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
linphone_core_manager_delete_chat_room(laure, laureCr, coresList);
linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
linphone_core_manager_destroy(laure);
}
static void group_chat_room_remove_admin(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *laure = linphone_core_manager_create("laure_tcp_rc");
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
coresManagerList = bctbx_list_append(coresManagerList, laure);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(laure->lc)));
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
stats initialLaureStats = laure->stat;
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
LinphoneChatRoom *marieCr =
create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject, FALSE,
LinphoneChatRoomEphemeralModeDeviceManaged);
const LinphoneAddress *confAddr = linphone_chat_room_get_conference_address(marieCr);
// Check that the chat room is correctly created on Pauline's side and that the participants are added
LinphoneChatRoom *paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats,
confAddr, initialSubject, 2, FALSE);
// Check that the chat room is correctly created on Laure's side and that the participants are added
LinphoneChatRoom *laureCr =
check_creation_chat_room_client_side(coresList, laure, &initialLaureStats, confAddr, initialSubject, 2, FALSE);
if (!BC_ASSERT_PTR_NOT_NULL(marieCr) || !BC_ASSERT_PTR_NOT_NULL(paulineCr) || !BC_ASSERT_PTR_NOT_NULL(laureCr))
goto end;
// Marie designates Pauline as admin
LinphoneAddress *paulineAddr = linphone_address_new(linphone_core_get_identity(pauline->lc));
LinphoneParticipant *paulineParticipant = linphone_chat_room_find_participant(marieCr, paulineAddr);
linphone_address_unref(paulineAddr);
BC_ASSERT_PTR_NOT_NULL(paulineParticipant);
linphone_chat_room_set_participant_admin_status(marieCr, paulineParticipant, TRUE);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_participant_admin_statuses_changed,
initialMarieStats.number_of_participant_admin_statuses_changed + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_participant_admin_statuses_changed,
initialPaulineStats.number_of_participant_admin_statuses_changed + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_participant_admin_statuses_changed,
2101210221032104210521062107210821092110211121122113211421152116211721182119212021212122212321242125212621272128212921302131213221332134213521362137213821392140214121422143214421452146214721482149215021512152215321542155215621572158215921602161216221632164216521662167216821692170
initialLaureStats.number_of_participant_admin_statuses_changed + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(linphone_participant_is_admin(paulineParticipant));
// Pauline revokes the admin status of Marie
LinphoneAddress *marieAddr = linphone_address_new(linphone_core_get_identity(marie->lc));
LinphoneParticipant *marieParticipant = linphone_chat_room_find_participant(paulineCr, marieAddr);
linphone_address_unref(marieAddr);
BC_ASSERT_PTR_NOT_NULL(marieParticipant);
linphone_chat_room_set_participant_admin_status(paulineCr, marieParticipant, FALSE);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_participant_admin_statuses_changed,
initialMarieStats.number_of_participant_admin_statuses_changed + 2,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_participant_admin_statuses_changed,
initialPaulineStats.number_of_participant_admin_statuses_changed + 2,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_participant_admin_statuses_changed,
initialLaureStats.number_of_participant_admin_statuses_changed + 2,
liblinphone_tester_sip_timeout));
BC_ASSERT_FALSE(linphone_participant_is_admin(marieParticipant));
end:
// Clean db from chat room
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
linphone_core_manager_delete_chat_room(laure, laureCr, coresList);
linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
linphone_core_manager_destroy(laure);
}
static void group_chat_room_admin_creator_leaves_the_room(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *laure = linphone_core_manager_create("laure_tcp_rc");
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
coresManagerList = bctbx_list_append(coresManagerList, laure);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(laure->lc)));
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
stats initialLaureStats = laure->stat;
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
LinphoneChatRoom *marieCr =
create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject, FALSE,
LinphoneChatRoomEphemeralModeDeviceManaged);
const LinphoneAddress *confAddr = linphone_chat_room_get_conference_address(marieCr);
// Check that the chat room is correctly created on Pauline's side and that the participants are added
LinphoneChatRoom *paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats,
confAddr, initialSubject, 2, FALSE);
// Check that the chat room is correctly created on Laure's side and that the participants are added
LinphoneChatRoom *laureCr =
check_creation_chat_room_client_side(coresList, laure, &initialLaureStats, confAddr, initialSubject, 2, FALSE);
if (!BC_ASSERT_PTR_NOT_NULL(marieCr) || !BC_ASSERT_PTR_NOT_NULL(paulineCr) || !BC_ASSERT_PTR_NOT_NULL(laureCr))
2171217221732174217521762177217821792180218121822183218421852186218721882189219021912192219321942195219621972198219922002201220222032204220522062207220822092210221122122213221422152216221722182219222022212222222322242225222622272228222922302231223222332234223522362237223822392240
goto end;
// Marie leaves the room
linphone_chat_room_leave(marieCr);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneConferenceStateTerminated,
initialMarieStats.number_of_LinphoneConferenceStateTerminated + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_participants_removed,
initialPaulineStats.number_of_participants_removed + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_participants_removed,
initialLaureStats.number_of_participants_removed + 1, liblinphone_tester_sip_timeout));
/* FIXME: the number of admin status changed shoud be 1. But the conference server notifies first that marie looses
* its admin status, before being deleted from the chatroom. This is indeed useless to notify this. Once fixed in
* the conference server, the counter shall be set back to +1. */
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_participant_admin_statuses_changed,
initialPaulineStats.number_of_participant_admin_statuses_changed + 2,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_participant_admin_statuses_changed,
initialLaureStats.number_of_participant_admin_statuses_changed + 2,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(linphone_participant_is_admin(linphone_chat_room_get_me(laureCr)));
end:
// Clean db from chat room
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
linphone_core_manager_delete_chat_room(laure, laureCr, coresList);
linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
linphone_core_manager_destroy(laure);
}
static void group_chat_room_change_subject(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *laure = linphone_core_manager_create("laure_tcp_rc");
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
coresManagerList = bctbx_list_append(coresManagerList, laure);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(laure->lc)));
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
stats initialLaureStats = laure->stat;
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
const char *newSubject = "New subject";
LinphoneChatRoom *marieCr =
create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject, FALSE,
LinphoneChatRoomEphemeralModeDeviceManaged);
const LinphoneAddress *confAddr = linphone_chat_room_get_conference_address(marieCr);
// Check that the chat room is correctly created on Pauline's side and that the participants are added
LinphoneChatRoom *paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats,
confAddr, initialSubject, 2, FALSE);
// Check that the chat room is correctly created on Laure's side and that the participants are added
LinphoneChatRoom *laureCr =
2241224222432244224522462247224822492250225122522253225422552256225722582259226022612262226322642265226622672268226922702271227222732274227522762277227822792280228122822283228422852286228722882289229022912292229322942295229622972298229923002301230223032304230523062307230823092310
check_creation_chat_room_client_side(coresList, laure, &initialLaureStats, confAddr, initialSubject, 2, FALSE);
if (!BC_ASSERT_PTR_NOT_NULL(marieCr) || !BC_ASSERT_PTR_NOT_NULL(paulineCr) || !BC_ASSERT_PTR_NOT_NULL(laureCr))
goto end;
// Marie now changes the subject
linphone_chat_room_set_subject(marieCr, newSubject);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_subject_changed,
initialMarieStats.number_of_subject_changed + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_subject_changed,
initialPaulineStats.number_of_subject_changed + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_subject_changed,
initialLaureStats.number_of_subject_changed + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_core_chat_room_subject_changed,
initialMarieStats.number_of_core_chat_room_subject_changed + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_core_chat_room_subject_changed,
initialPaulineStats.number_of_core_chat_room_subject_changed + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_core_chat_room_subject_changed,
initialLaureStats.number_of_core_chat_room_subject_changed + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(marieCr), newSubject);
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(paulineCr), newSubject);
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(laureCr), newSubject);
// Clean db from chat room
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
linphone_core_manager_delete_chat_room(laure, laureCr, coresList);
linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
end:
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
linphone_core_manager_destroy(laure);
}
static void group_chat_room_change_subject_non_admin(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *laure = linphone_core_manager_create("laure_tcp_rc");
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
coresManagerList = bctbx_list_append(coresManagerList, laure);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(laure->lc)));
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
stats initialLaureStats = laure->stat;
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
const char *newSubject = "New subject";
LinphoneChatRoom *marieCr =
create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject, FALSE,
LinphoneChatRoomEphemeralModeDeviceManaged);
const LinphoneAddress *confAddr = linphone_chat_room_get_conference_address(marieCr);
// Check that the chat room is correctly created on Pauline's side and that the participants are added
LinphoneChatRoom *paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats,
confAddr, initialSubject, 2, FALSE);
// Check that the chat room is correctly created on Laure's side and that the participants are added
2311231223132314231523162317231823192320232123222323232423252326232723282329233023312332233323342335233623372338233923402341234223432344234523462347234823492350235123522353235423552356235723582359236023612362236323642365236623672368236923702371237223732374237523762377237823792380
LinphoneChatRoom *laureCr =
check_creation_chat_room_client_side(coresList, laure, &initialLaureStats, confAddr, initialSubject, 2, FALSE);
if (!BC_ASSERT_PTR_NOT_NULL(marieCr) || !BC_ASSERT_PTR_NOT_NULL(paulineCr) || !BC_ASSERT_PTR_NOT_NULL(laureCr))
goto end;
// Marie now changes the subject
linphone_chat_room_set_subject(paulineCr, newSubject);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_subject_changed,
initialMarieStats.number_of_subject_changed, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_subject_changed,
initialPaulineStats.number_of_subject_changed, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_subject_changed,
initialLaureStats.number_of_subject_changed, liblinphone_tester_sip_timeout));
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(marieCr), initialSubject);
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(paulineCr), initialSubject);
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(laureCr), initialSubject);
// Clean db from chat room
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
linphone_core_manager_delete_chat_room(laure, laureCr, coresList);
linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
end:
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
linphone_core_manager_destroy(laure);
}
static void group_chat_room_remove_participant_base(bool_t restart) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *laure = linphone_core_manager_create("laure_tcp_rc");
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
coresManagerList = bctbx_list_append(coresManagerList, laure);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(laure->lc)));
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
stats initialLaureStats = laure->stat;
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
LinphoneChatRoom *marieCr =
create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject, FALSE,
LinphoneChatRoomEphemeralModeDeviceManaged);
LinphoneAddress *confAddr = linphone_address_clone(linphone_chat_room_get_conference_address(marieCr));
// Check that the chat room is correctly created on Pauline's side and that the participants are added
LinphoneChatRoom *paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats,
confAddr, initialSubject, 2, FALSE);
// Check that the chat room is correctly created on Laure's side and that the participants are added
LinphoneChatRoom *laureCr =
check_creation_chat_room_client_side(coresList, laure, &initialLaureStats, confAddr, initialSubject, 2, FALSE);
if (!BC_ASSERT_PTR_NOT_NULL(marieCr) || !BC_ASSERT_PTR_NOT_NULL(paulineCr) || !BC_ASSERT_PTR_NOT_NULL(laureCr))
goto end;
// Marie removes Laure from the chat room
LinphoneAddress *laureAddr = linphone_address_new(linphone_core_get_identity(laure->lc));
LinphoneParticipant *laureParticipant = linphone_chat_room_find_participant(marieCr, laureAddr);
linphone_address_unref(laureAddr);
2381238223832384238523862387238823892390239123922393239423952396239723982399240024012402240324042405240624072408240924102411241224132414241524162417241824192420242124222423242424252426242724282429243024312432243324342435243624372438243924402441244224432444244524462447244824492450
BC_ASSERT_PTR_NOT_NULL(laureParticipant);
linphone_chat_room_remove_participant(marieCr, laureParticipant);
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_LinphoneConferenceStateTerminated,
initialLaureStats.number_of_LinphoneConferenceStateTerminated + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_participants_removed,
initialMarieStats.number_of_participants_removed + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_participants_removed,
initialPaulineStats.number_of_participants_removed + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(marieCr), 1, int, "%d");
if (restart == TRUE) {
// Restart core for Marie
coresList = bctbx_list_remove(coresList, marie->lc);
linphone_core_manager_restart(marie, TRUE);
bctbx_list_t *tmpCoresManagerList = bctbx_list_append(NULL, marie);
init_core_for_conference(tmpCoresManagerList);
bctbx_list_free(tmpCoresManagerList);
coresList = bctbx_list_append(coresList, marie->lc);
// Retrieve chat room
LinphoneAddress *marieDeviceAddr = linphone_address_clone(
linphone_proxy_config_get_contact(linphone_core_get_default_proxy_config(marie->lc)));
marieCr = linphone_core_search_chat_room(marie->lc, NULL, marieDeviceAddr, confAddr, NULL);
linphone_address_unref(marieDeviceAddr);
BC_ASSERT_PTR_NOT_NULL(marieCr);
}
// Check that participant removed event has been stored
// Passing 0 as second argument because all events must be retrived
int nbMarieParticipantRemoved = 0;
bctbx_list_t *marieHistory = linphone_chat_room_get_history_events(marieCr, 0);
for (bctbx_list_t *item = marieHistory; item; item = bctbx_list_next(item)) {
LinphoneEventLog *event = (LinphoneEventLog *)bctbx_list_get_data(item);
if (linphone_event_log_get_type(event) == LinphoneEventLogTypeConferenceParticipantRemoved) {
nbMarieParticipantRemoved++;
const LinphoneAddress *removedParticipantAddress = linphone_event_log_get_participant_address(event);
BC_ASSERT_PTR_NOT_NULL(removedParticipantAddress);
}
}
bctbx_list_free_with_data(marieHistory, (bctbx_list_free_func)linphone_event_log_unref);
BC_ASSERT_EQUAL(nbMarieParticipantRemoved, 1, unsigned int, "%u");
linphone_address_unref(confAddr);
// Clean db from chat room
linphone_core_delete_chat_room(marie->lc, marieCr);
linphone_core_manager_delete_chat_room(laure, laureCr, coresList);
linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
end:
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
linphone_core_manager_destroy(laure);
}
static void group_chat_room_remove_participant(void) {
group_chat_room_remove_participant_base(FALSE);
}
static void group_chat_room_remove_participant_and_restart(void) {
group_chat_room_remove_participant_base(TRUE);
}
static void group_chat_room_send_message_with_participant_removed(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *laure = linphone_core_manager_create("laure_tcp_rc");
2451245224532454245524562457245824592460246124622463246424652466246724682469247024712472247324742475247624772478247924802481248224832484248524862487248824892490249124922493249424952496249724982499250025012502250325042505250625072508250925102511251225132514251525162517251825192520
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
coresManagerList = bctbx_list_append(coresManagerList, laure);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(laure->lc)));
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
stats initialLaureStats = laure->stat;
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
LinphoneChatRoom *marieCr =
create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject, FALSE,
LinphoneChatRoomEphemeralModeDeviceManaged);
const LinphoneAddress *confAddr = linphone_chat_room_get_conference_address(marieCr);
// Check that the chat room is correctly created on Pauline's side and that the participants are added
LinphoneChatRoom *paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats,
confAddr, initialSubject, 2, FALSE);
// Check that the chat room is correctly created on Laure's side and that the participants are added
LinphoneChatRoom *laureCr =
check_creation_chat_room_client_side(coresList, laure, &initialLaureStats, confAddr, initialSubject, 2, FALSE);
if (!BC_ASSERT_PTR_NOT_NULL(marieCr) || !BC_ASSERT_PTR_NOT_NULL(paulineCr) || !BC_ASSERT_PTR_NOT_NULL(laureCr))
goto end;
// Marie removes Laure from the chat room
LinphoneAddress *laureAddr = linphone_address_new(linphone_core_get_identity(laure->lc));
LinphoneParticipant *laureParticipant = linphone_chat_room_find_participant(marieCr, laureAddr);
linphone_address_unref(laureAddr);
if (!BC_ASSERT_PTR_NOT_NULL(laureParticipant)) goto end;
linphone_chat_room_remove_participant(marieCr, laureParticipant);
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_LinphoneConferenceStateTerminated,
initialLaureStats.number_of_LinphoneConferenceStateTerminated + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_participants_removed,
initialMarieStats.number_of_participants_removed + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_participants_removed,
initialPaulineStats.number_of_participants_removed + 1,
liblinphone_tester_sip_timeout));
// Laure try to send a message with the chat room where she was removed
const char *laureTextMessage = "Hello";
LinphoneChatMessage *laureMessage = _send_message(laureCr, laureTextMessage);
linphone_chat_message_unref(laureMessage);
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_LinphoneMessageReceived,
initialMarieStats.number_of_LinphoneMessageDelivered, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneMessageReceived,
initialMarieStats.number_of_LinphoneMessageReceived, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageReceived,
initialPaulineStats.number_of_LinphoneMessageReceived,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneIsComposingIdleReceived,
initialMarieStats.number_of_LinphoneIsComposingIdleReceived,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneIsComposingIdleReceived,
initialPaulineStats.number_of_LinphoneIsComposingIdleReceived,
liblinphone_tester_sip_timeout));
end:
// Clean db from chat room
2521252225232524252525262527252825292530253125322533253425352536253725382539254025412542254325442545254625472548254925502551255225532554255525562557255825592560256125622563256425652566256725682569257025712572257325742575257625772578257925802581258225832584258525862587258825892590
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
linphone_core_manager_delete_chat_room(laure, laureCr, coresList);
linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
linphone_core_manager_destroy(laure);
}
static void group_chat_room_leave(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *laure = linphone_core_manager_create("laure_tcp_rc");
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
coresManagerList = bctbx_list_append(coresManagerList, laure);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(laure->lc)));
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
stats initialLaureStats = laure->stat;
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
LinphoneChatRoom *marieCr =
create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject, FALSE,
LinphoneChatRoomEphemeralModeDeviceManaged);
const LinphoneAddress *confAddr = linphone_chat_room_get_conference_address(marieCr);
// Check that the chat room is correctly created on Pauline's side and that the participants are added
LinphoneChatRoom *paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats,
confAddr, initialSubject, 2, FALSE);
// Check that the chat room is correctly created on Laure's side and that the participants are added
LinphoneChatRoom *laureCr =
check_creation_chat_room_client_side(coresList, laure, &initialLaureStats, confAddr, initialSubject, 2, FALSE);
BC_ASSERT_FALSE(linphone_chat_room_is_read_only(marieCr));
BC_ASSERT_FALSE(linphone_chat_room_is_read_only(paulineCr));
BC_ASSERT_FALSE(linphone_chat_room_is_read_only(laureCr));
linphone_chat_room_leave(paulineCr);
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneConferenceStateTerminated,
initialPaulineStats.number_of_LinphoneConferenceStateTerminated + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_participants_removed,
initialMarieStats.number_of_participants_removed + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_participants_removed,
initialLaureStats.number_of_participants_removed + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(linphone_chat_room_is_read_only(paulineCr));
// Clean db from chat room
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
linphone_core_manager_delete_chat_room(laure, laureCr, coresList);
linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
linphone_core_manager_destroy(laure);
2591259225932594259525962597259825992600260126022603260426052606260726082609261026112612261326142615261626172618261926202621262226232624262526262627262826292630263126322633263426352636263726382639264026412642264326442645264626472648264926502651265226532654265526562657265826592660
}
static void group_chat_room_delete_twice(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *laure = linphone_core_manager_create("laure_tcp_rc");
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
coresManagerList = bctbx_list_append(coresManagerList, laure);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(laure->lc)));
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
stats initialLaureStats = laure->stat;
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
LinphoneChatRoom *marieCr =
create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject, FALSE,
LinphoneChatRoomEphemeralModeDeviceManaged);
const LinphoneAddress *confAddr = linphone_chat_room_get_conference_address(marieCr);
// Check that the chat room is correctly created on Pauline's side and that the participants are added
LinphoneChatRoom *paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats,
confAddr, initialSubject, 2, FALSE);
// Check that the chat room is correctly created on Laure's side and that the participants are added
LinphoneChatRoom *laureCr =
check_creation_chat_room_client_side(coresList, laure, &initialLaureStats, confAddr, initialSubject, 2, FALSE);
if (!BC_ASSERT_PTR_NOT_NULL(marieCr) || !BC_ASSERT_PTR_NOT_NULL(paulineCr) || !BC_ASSERT_PTR_NOT_NULL(laureCr))
goto end;
// Save db
const char *uri = linphone_config_get_string(linphone_core_get_config(laure->lc), "storage", "uri", "");
char *uriCopy = bc_tester_file("linphone_tester.db");
BC_ASSERT_FALSE(liblinphone_tester_copy_file(uri, uriCopy));
// Clean db from chat room
linphone_core_manager_delete_chat_room(laure, laureCr, coresList);
// Reset db
laure->database_path = uriCopy;
coresList = bctbx_list_remove(coresList, laure->lc);
linphone_core_manager_reinit(laure);
bctbx_list_t *tmpCoresManagerList = bctbx_list_append(NULL, laure);
bctbx_list_t *tmpCoresList = init_core_for_conference(tmpCoresManagerList);
bctbx_list_free(tmpCoresManagerList);
coresList = bctbx_list_concat(coresList, tmpCoresList);
linphone_core_manager_start(laure, TRUE);
// Check that the chat room has correctly created on Laure's side and that the participants are added
laureCr = check_has_chat_room_client_side(coresList, laure, &initialLaureStats, confAddr, initialSubject, 2, FALSE);
end:
// Clean db from chat room again
linphone_core_manager_delete_chat_room(laure, laureCr, coresList);
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
linphone_core_manager_destroy(laure);
2661266226632664266526662667266826692670267126722673267426752676267726782679268026812682268326842685268626872688268926902691269226932694269526962697269826992700270127022703270427052706270727082709271027112712271327142715271627172718271927202721272227232724272527262727272827292730
}
static void group_chat_room_come_back_after_disconnection(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *laure = linphone_core_manager_create("laure_tcp_rc");
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
int dummy = 0;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
coresManagerList = bctbx_list_append(coresManagerList, laure);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(laure->lc)));
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
stats initialLaureStats = laure->stat;
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
const char *newSubject = "New subject";
LinphoneChatRoom *marieCr =
create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject, FALSE,
LinphoneChatRoomEphemeralModeDeviceManaged);
const LinphoneAddress *confAddr = linphone_chat_room_get_conference_address(marieCr);
// Check that the chat room is correctly created on Pauline's side and that the participants are added
LinphoneChatRoom *paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats,
confAddr, initialSubject, 2, FALSE);
// Check that the chat room is correctly created on Laure's side and that the participants are added
LinphoneChatRoom *laureCr =
check_creation_chat_room_client_side(coresList, laure, &initialLaureStats, confAddr, initialSubject, 2, FALSE);
if (!BC_ASSERT_PTR_NOT_NULL(marieCr) || !BC_ASSERT_PTR_NOT_NULL(paulineCr) || !BC_ASSERT_PTR_NOT_NULL(laureCr))
goto end;
linphone_core_set_network_reachable(marie->lc, FALSE);
wait_for_list(coresList, &dummy, 1, 1000);
linphone_core_set_network_reachable(marie->lc, TRUE);
wait_for_list(coresList, &dummy, 1, 1000);
// Marie now changes the subject
linphone_chat_room_set_subject(marieCr, newSubject);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_subject_changed,
initialMarieStats.number_of_subject_changed + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_subject_changed,
initialPaulineStats.number_of_subject_changed + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_subject_changed,
initialLaureStats.number_of_subject_changed + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(marieCr), newSubject);
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(paulineCr), newSubject);
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(laureCr), newSubject);
end:
// Clean db from chat room
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
linphone_core_manager_delete_chat_room(laure, laureCr, coresList);
linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
2731273227332734273527362737273827392740274127422743274427452746274727482749275027512752275327542755275627572758275927602761276227632764276527662767276827692770277127722773277427752776277727782779278027812782278327842785278627872788278927902791279227932794279527962797279827992800
linphone_core_manager_destroy(laure);
}
static void group_chat_room_create_room_with_disconnected_friends_base(bool_t initial_message) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *laure = linphone_core_manager_create("laure_tcp_rc");
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
int dummy = 0;
LinphoneChatRoom *paulineCr = NULL;
LinphoneChatRoom *laureCr = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
coresManagerList = bctbx_list_append(coresManagerList, laure);
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
stats initialLaureStats = laure->stat;
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
wait_for_list(coresList, &dummy, 1, 2000);
// Disconnect pauline and laure
linphone_core_set_network_reachable(pauline->lc, FALSE);
linphone_core_set_network_reachable(laure->lc, FALSE);
wait_for_list(coresList, &dummy, 1, 2000);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(laure->lc)));
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
LinphoneChatRoom *marieCr =
create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject, FALSE,
LinphoneChatRoomEphemeralModeDeviceManaged);
const LinphoneAddress *confAddr = linphone_chat_room_get_conference_address(marieCr);
if (initial_message) {
LinphoneChatMessage *msg = linphone_chat_room_create_message_from_utf8(marieCr, "Salut");
linphone_chat_message_send(msg);
linphone_chat_message_unref(msg);
}
wait_for_list(coresList, &dummy, 1, 4000);
// Reconnect Pauline and check that the chat room is correctly created on Pauline's side and that the participants
// are added
linphone_core_set_network_reachable(pauline->lc, TRUE);
paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats, confAddr, initialSubject,
2, FALSE);
if (!BC_ASSERT_PTR_NOT_NULL(paulineCr)) goto end;
// Reconnect Laure and check that the chat room is correctly created on Laure's side and that the participants are
// added
linphone_core_set_network_reachable(laure->lc, TRUE);
laureCr =
check_creation_chat_room_client_side(coresList, laure, &initialLaureStats, confAddr, initialSubject, 2, FALSE);
if (!BC_ASSERT_PTR_NOT_NULL(laureCr)) goto end;
if (initial_message) {
if (BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageReceived, 1,
liblinphone_tester_sip_timeout))) {
LinphoneChatMessage *msg = linphone_chat_room_get_last_message_in_history(paulineCr);
2801280228032804280528062807280828092810281128122813281428152816281728182819282028212822282328242825282628272828282928302831283228332834283528362837283828392840284128422843284428452846284728482849285028512852285328542855285628572858285928602861286228632864286528662867286828692870
if (BC_ASSERT_PTR_NOT_NULL(msg)) {
BC_ASSERT_STRING_EQUAL(linphone_chat_message_get_text(msg), "Salut");
linphone_chat_message_unref(msg);
}
}
if (BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_LinphoneMessageReceived, 1,
liblinphone_tester_sip_timeout))) {
LinphoneChatMessage *msg = linphone_chat_room_get_last_message_in_history(laureCr);
if (BC_ASSERT_PTR_NOT_NULL(msg)) {
BC_ASSERT_STRING_EQUAL(linphone_chat_message_get_text(msg), "Salut");
linphone_chat_message_unref(msg);
}
}
}
end:
// Clean db from chat room
if (marieCr) linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
if (laureCr) linphone_core_manager_delete_chat_room(laure, laureCr, coresList);
if (paulineCr) linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
linphone_core_manager_destroy(laure);
}
static void group_chat_room_create_room_with_disconnected_friends(void) {
group_chat_room_create_room_with_disconnected_friends_base(FALSE);
}
static void group_chat_room_create_room_with_disconnected_friends_and_initial_message(void) {
group_chat_room_create_room_with_disconnected_friends_base(TRUE);
}
static void group_chat_room_reinvited_after_removed_base(bool_t offline_when_removed,
bool_t offline_when_reinvited,
bool_t restart_after_reinvited) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *laure = linphone_core_manager_create("laure_tcp_rc");
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
coresManagerList = bctbx_list_append(coresManagerList, laure);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
const char *marieIdentity = linphone_core_get_identity(marie->lc);
const char *paulineIdentity = linphone_core_get_identity(pauline->lc);
const char *laureIdentity = linphone_core_get_identity(laure->lc);
participantsAddresses = bctbx_list_append(participantsAddresses, linphone_address_new(paulineIdentity));
participantsAddresses = bctbx_list_append(participantsAddresses, linphone_address_new(laureIdentity));
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
stats initialLaureStats = laure->stat;
char *savedLaureUuid = NULL;
char *laureParticipantAddress = NULL;
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
LinphoneChatRoom *marieCr =
create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject, FALSE,
LinphoneChatRoomEphemeralModeDeviceManaged);
participantsAddresses = NULL;
const LinphoneAddress *confAddr = linphone_chat_room_get_conference_address(marieCr);
2871287228732874287528762877287828792880288128822883288428852886288728882889289028912892289328942895289628972898289929002901290229032904290529062907290829092910291129122913291429152916291729182919292029212922292329242925292629272928292929302931293229332934293529362937293829392940
char *conference_address_str = (confAddr) ? linphone_address_as_string(confAddr) : ms_strdup("<unknown>");
// Check that the chat room is correctly created on Pauline's side and that the participants are added
LinphoneChatRoom *paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats,
confAddr, initialSubject, 2, FALSE);
LinphoneChatRoom *newLaureCr = NULL;
// Check that the chat room is correctly created on Laure's side and that the participants are added
LinphoneChatRoom *laureCr =
check_creation_chat_room_client_side(coresList, laure, &initialLaureStats, confAddr, initialSubject, 2, FALSE);
if (!BC_ASSERT_PTR_NOT_NULL(marieCr) || !BC_ASSERT_PTR_NOT_NULL(paulineCr) || !BC_ASSERT_PTR_NOT_NULL(laureCr))
goto end;
LinphoneAddress *laureAddr = linphone_address_new(laureIdentity);
laureParticipantAddress = linphone_address_as_string(laureAddr);
if (offline_when_removed) {
savedLaureUuid =
bctbx_strdup(linphone_config_get_string(linphone_core_get_config(laure->lc), "misc", "uuid", NULL));
coresList = bctbx_list_remove(coresList, laure->lc);
coresManagerList = bctbx_list_remove(coresManagerList, laure);
linphone_core_set_network_reachable(laure->lc, FALSE);
linphone_core_manager_stop(laure);
}
// Marie removes Laure from the chat room
LinphoneParticipant *laureParticipant = linphone_chat_room_find_participant(marieCr, laureAddr);
BC_ASSERT_PTR_NOT_NULL(laureParticipant);
ms_message("%s removes %s to chatroom %s", marieIdentity, laureParticipantAddress, conference_address_str);
linphone_chat_room_remove_participant(marieCr, laureParticipant);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_participants_removed,
initialMarieStats.number_of_participants_removed + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_participants_removed,
initialPaulineStats.number_of_participants_removed + 1,
liblinphone_tester_sip_timeout));
if (offline_when_removed && !offline_when_reinvited) {
wait_for_list(coresList, 0, 1, 20000); /* see large comment below, also applicable for BYE */
linphone_core_manager_configure(laure);
linphone_config_set_string(linphone_core_get_config(laure->lc), "misc", "uuid", savedLaureUuid);
bctbx_free(savedLaureUuid);
bctbx_list_t *tmpCoresManagerList = bctbx_list_append(NULL, laure);
bctbx_list_t *tmpCoresList = init_core_for_conference(tmpCoresManagerList);
bctbx_list_free(tmpCoresManagerList);
linphone_core_manager_start(laure, TRUE);
laureIdentity = linphone_core_get_identity(laure->lc);
coresList = bctbx_list_concat(coresList, tmpCoresList);
coresManagerList = bctbx_list_append(coresManagerList, laure);
}
if (!offline_when_reinvited) {
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_LinphoneConferenceStateTerminated,
initialLaureStats.number_of_LinphoneConferenceStateTerminated + 1,
liblinphone_tester_sip_timeout));
}
wait_for_list(coresList, 0, 1, 2000);
initialLaureStats = laure->stat;
// Marie adds Laure to the chat room
ms_message("%s adds %s to chatroom %s", marieIdentity, laureParticipantAddress, conference_address_str);
participantsAddresses = bctbx_list_append(participantsAddresses, laureAddr);
linphone_chat_room_add_participants(marieCr, participantsAddresses);
bctbx_list_free_with_data(participantsAddresses, (bctbx_list_free_func)linphone_address_unref);
participantsAddresses = NULL;
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_participants_added,
initialMarieStats.number_of_participants_added + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_participants_added,
initialPaulineStats.number_of_participants_added + 1, liblinphone_tester_sip_timeout));
if (offline_when_reinvited) {
/*
* Hack: while we were offline the server sent an INVITE, that will get a 408 timeout after 20 seconds.
2941294229432944294529462947294829492950295129522953295429552956295729582959296029612962296329642965296629672968296929702971297229732974297529762977297829792980298129822983298429852986298729882989299029912992299329942995299629972998299930003001300230033004300530063007300830093010
* During this time, the REGISTER from Laure won't trigger a new INVITE.
* FIXME: it should be handled at server side.
* However, since the case isn't very real-world probable, we can workaround it in the test by waiting this
* INVITE to timeout, and then REGISTER.
* */
wait_for_list(coresList, 0, 1, 20000);
linphone_core_manager_configure(laure);
linphone_config_set_string(linphone_core_get_config(laure->lc), "misc", "uuid", savedLaureUuid);
bctbx_free(savedLaureUuid);
bctbx_list_t *tmpCoresManagerList = bctbx_list_append(NULL, laure);
bctbx_list_t *tmpCoresList = init_core_for_conference(tmpCoresManagerList);
bctbx_list_free(tmpCoresManagerList);
linphone_core_manager_start(laure, TRUE);
coresList = bctbx_list_concat(coresList, tmpCoresList);
coresManagerList = bctbx_list_append(coresManagerList, laure);
}
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_LinphoneConferenceStateCreated,
initialLaureStats.number_of_LinphoneConferenceStateCreated + 1, 10000));
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(marieCr), 2, int, "%d");
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(paulineCr), 2, int, "%d");
char *laureDeviceIdentity = linphone_core_get_device_identity(laure->lc);
laureAddr = linphone_address_new(laureDeviceIdentity);
bctbx_free(laureDeviceIdentity);
newLaureCr = linphone_core_find_chat_room(laure->lc, confAddr, laureAddr);
linphone_address_unref(laureAddr);
if (!offline_when_removed) BC_ASSERT_PTR_EQUAL(newLaureCr, laureCr);
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(newLaureCr), 2, int, "%d");
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(newLaureCr), initialSubject);
BC_ASSERT_FALSE(linphone_chat_room_has_been_left(newLaureCr));
unsigned int nbLaureConferenceCreatedEventsBeforeRestart = 0;
bctbx_list_t *laureHistory = linphone_chat_room_get_history_events(newLaureCr, 0);
for (bctbx_list_t *item = laureHistory; item; item = bctbx_list_next(item)) {
LinphoneEventLog *event = (LinphoneEventLog *)bctbx_list_get_data(item);
if (linphone_event_log_get_type(event) == LinphoneEventLogTypeConferenceCreated)
nbLaureConferenceCreatedEventsBeforeRestart++;
}
bctbx_list_free_with_data(laureHistory, (bctbx_list_free_func)linphone_event_log_unref);
// Restarting Laure's core doesn't generate a second ConferenceCreated event
BC_ASSERT_EQUAL(nbLaureConferenceCreatedEventsBeforeRestart, 1, unsigned int, "%u");
if (restart_after_reinvited) {
ms_message("%s restarts its core", laureIdentity);
coresList = bctbx_list_remove(coresList, laure->lc);
linphone_core_manager_reinit(laure);
bctbx_list_t *tmpCoresManagerList = bctbx_list_append(NULL, laure);
bctbx_list_t *tmpCoresList = init_core_for_conference(tmpCoresManagerList);
bctbx_list_free(tmpCoresManagerList);
coresList = bctbx_list_concat(coresList, tmpCoresList);
linphone_core_manager_start(laure, TRUE);
laureIdentity = linphone_core_get_device_identity(laure->lc);
laureAddr = linphone_address_new(laureIdentity);
newLaureCr = linphone_core_find_chat_room(laure->lc, confAddr, laureAddr);
linphone_address_unref(laureAddr);
wait_for_list(coresList, 0, 1, 2000);
BC_ASSERT_FALSE(linphone_chat_room_has_been_left(newLaureCr));
unsigned int nbLaureConferenceCreatedEventsAfterRestart = 0;
bctbx_list_t *laureHistory = linphone_chat_room_get_history_events(newLaureCr, 0);
for (bctbx_list_t *item = laureHistory; item; item = bctbx_list_next(item)) {
LinphoneEventLog *event = (LinphoneEventLog *)bctbx_list_get_data(item);
if (linphone_event_log_get_type(event) == LinphoneEventLogTypeConferenceCreated)
nbLaureConferenceCreatedEventsAfterRestart++;
}
bctbx_list_free_with_data(laureHistory, (bctbx_list_free_func)linphone_event_log_unref);
BC_ASSERT_EQUAL(nbLaureConferenceCreatedEventsAfterRestart, nbLaureConferenceCreatedEventsBeforeRestart + 1,
unsigned int, "%u");
}
end:
// Clean db from chat room
3011301230133014301530163017301830193020302130223023302430253026302730283029303030313032303330343035303630373038303930403041304230433044304530463047304830493050305130523053305430553056305730583059306030613062306330643065306630673068306930703071307230733074307530763077307830793080
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
linphone_core_manager_delete_chat_room(laure, newLaureCr, coresList);
linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
ms_free(conference_address_str);
if (laureParticipantAddress) ms_free(laureParticipantAddress);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
linphone_core_manager_destroy(laure);
}
static void group_chat_room_reinvited_after_removed(void) {
group_chat_room_reinvited_after_removed_base(FALSE, FALSE, FALSE);
}
static void group_chat_room_reinvited_after_removed_2(void) {
group_chat_room_reinvited_after_removed_base(FALSE, FALSE, TRUE);
}
static void group_chat_room_reinvited_after_removed_while_offline(void) {
group_chat_room_reinvited_after_removed_base(TRUE, FALSE, FALSE);
}
static void group_chat_room_reinvited_after_removed_while_offline_2(void) {
group_chat_room_reinvited_after_removed_base(TRUE, TRUE, FALSE);
}
static void group_chat_room_reinvited_after_removed_with_several_devices(void) {
LinphoneCoreManager *marie1 = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *marie2 = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline1 = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *pauline2 = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *laure = linphone_core_manager_create("laure_tcp_rc");
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie1);
coresManagerList = bctbx_list_append(coresManagerList, marie2);
coresManagerList = bctbx_list_append(coresManagerList, pauline1);
coresManagerList = bctbx_list_append(coresManagerList, pauline2);
coresManagerList = bctbx_list_append(coresManagerList, laure);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline1->lc)));
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(laure->lc)));
stats initialMarie1Stats = marie1->stat;
stats initialMarie2Stats = marie2->stat;
stats initialPauline1Stats = pauline1->stat;
stats initialPauline2Stats = pauline2->stat;
stats initialLaureStats = laure->stat;
// Marie2 is initially offline
linphone_core_set_network_reachable(marie2->lc, FALSE);
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
LinphoneChatRoom *marie1Cr =
create_chat_room_client_side(coresList, marie1, &initialMarie1Stats, participantsAddresses, initialSubject,
FALSE, LinphoneChatRoomEphemeralModeDeviceManaged);
LinphoneChatRoom *marie2Cr = NULL;
participantsAddresses = NULL;
const LinphoneAddress *confAddr = linphone_chat_room_get_conference_address(marie1Cr);
// Check that the chat room is correctly created on Pauline1 and Pauline2's sides and that the participants are
// added
LinphoneChatRoom *pauline1Cr = check_creation_chat_room_client_side(coresList, pauline1, &initialPauline1Stats,
3081308230833084308530863087308830893090309130923093309430953096309730983099310031013102310331043105310631073108310931103111311231133114311531163117311831193120312131223123312431253126312731283129313031313132313331343135313631373138313931403141314231433144314531463147314831493150
confAddr, initialSubject, 2, FALSE);
LinphoneChatRoom *pauline2Cr = check_creation_chat_room_client_side(coresList, pauline2, &initialPauline2Stats,
confAddr, initialSubject, 2, FALSE);
LinphoneChatRoom *newPauline1Cr = NULL;
// Check that the chat room is correctly created on Laure's side and that the participants are added
LinphoneChatRoom *laureCr =
check_creation_chat_room_client_side(coresList, laure, &initialLaureStats, confAddr, initialSubject, 2, FALSE);
if (!BC_ASSERT_PTR_NOT_NULL(marie1Cr) || !BC_ASSERT_PTR_NOT_NULL(pauline1Cr) ||
!BC_ASSERT_PTR_NOT_NULL(pauline2Cr) || !BC_ASSERT_PTR_NOT_NULL(laureCr))
goto end;
// Marie1 removes Pauline from the chat room while Pauline2 is offline
linphone_core_set_network_reachable(pauline2->lc, FALSE);
LinphoneAddress *paulineAddr = linphone_address_new(linphone_core_get_identity(pauline1->lc));
LinphoneParticipant *paulineParticipant = linphone_chat_room_find_participant(marie1Cr, paulineAddr);
BC_ASSERT_PTR_NOT_NULL(paulineParticipant);
linphone_chat_room_remove_participant(marie1Cr, paulineParticipant);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie1->stat.number_of_participants_removed,
initialMarie1Stats.number_of_participants_removed + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_participants_removed,
initialLaureStats.number_of_participants_removed + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline1->stat.number_of_LinphoneConferenceStateTerminated,
initialPauline1Stats.number_of_LinphoneConferenceStateTerminated + 1,
liblinphone_tester_sip_timeout));
// Marie2 comes online, check that pauline is not notified as still being in the chat room
linphone_core_set_network_reachable(marie2->lc, TRUE);
marie2Cr =
check_creation_chat_room_client_side(coresList, marie2, &initialMarie2Stats, confAddr, initialSubject, 1, TRUE);
// Marie2 adds Pauline back to the chat room
initialPauline1Stats = pauline1->stat;
participantsAddresses = bctbx_list_append(participantsAddresses, paulineAddr);
linphone_chat_room_add_participants(marie2Cr, participantsAddresses);
bctbx_list_free_with_data(participantsAddresses, (bctbx_list_free_func)linphone_address_unref);
participantsAddresses = NULL;
BC_ASSERT_TRUE(wait_for_list(coresList, &marie1->stat.number_of_participants_added,
initialMarie1Stats.number_of_participants_added + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &marie2->stat.number_of_participants_added,
initialMarie2Stats.number_of_participants_added + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_participants_added,
initialLaureStats.number_of_participants_added + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(marie1Cr), 2, int, "%d");
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(marie2Cr), 2, int, "%d");
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(laureCr), 2, int, "%d");
newPauline1Cr = check_creation_chat_room_client_side(coresList, pauline1, &initialPauline1Stats, confAddr,
initialSubject, 2, FALSE);
BC_ASSERT_PTR_EQUAL(newPauline1Cr, pauline1Cr);
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(newPauline1Cr), 2, int, "%d");
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(newPauline1Cr), initialSubject);
end:
// Clean chat room from db
linphone_core_set_network_reachable(pauline2->lc, TRUE);
linphone_core_manager_delete_chat_room(marie1, marie1Cr, coresList);
linphone_core_delete_chat_room(marie2->lc, marie2Cr);
initialPauline2Stats = pauline2->stat;
linphone_core_manager_delete_chat_room(pauline1, newPauline1Cr, coresList);
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline2->stat.number_of_LinphoneConferenceStateTerminated,
initialPauline2Stats.number_of_LinphoneConferenceStateTerminated + 1,
liblinphone_tester_sip_timeout));
linphone_core_delete_chat_room(pauline2->lc, pauline2Cr);
linphone_core_manager_delete_chat_room(laure, laureCr, coresList);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie1);
linphone_core_manager_destroy(marie2);
linphone_core_manager_destroy(pauline1);
3151315231533154315531563157315831593160316131623163316431653166316731683169317031713172317331743175317631773178317931803181318231833184318531863187318831893190319131923193319431953196319731983199320032013202320332043205320632073208320932103211321232133214321532163217321832193220
linphone_core_manager_destroy(pauline2);
linphone_core_manager_destroy(laure);
}
static void group_chat_room_notify_after_disconnection(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *laure = linphone_core_manager_create("laure_tcp_rc");
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
int dummy = 0;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
coresManagerList = bctbx_list_append(coresManagerList, laure);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(laure->lc)));
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
stats initialLaureStats = laure->stat;
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
LinphoneChatRoom *marieCr =
create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject, FALSE,
LinphoneChatRoomEphemeralModeDeviceManaged);
BC_ASSERT_PTR_NOT_NULL(marieCr);
participantsAddresses = NULL;
const LinphoneAddress *confAddr = linphone_chat_room_get_conference_address(marieCr);
// Check that the chat room is correctly created on Pauline's side and that the participants are added
LinphoneChatRoom *paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats,
confAddr, initialSubject, 2, FALSE);
BC_ASSERT_PTR_NOT_NULL(paulineCr);
// Check that the chat room is correctly created on Laure's side and that the participants are added
LinphoneChatRoom *laureCr =
check_creation_chat_room_client_side(coresList, laure, &initialLaureStats, confAddr, initialSubject, 2, FALSE);
BC_ASSERT_PTR_NOT_NULL(laureCr);
// Marie now changes the subject
const char *newSubject = "New subject";
linphone_chat_room_set_subject(marieCr, newSubject);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_subject_changed,
initialMarieStats.number_of_subject_changed + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_subject_changed,
initialPaulineStats.number_of_subject_changed + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_subject_changed,
initialLaureStats.number_of_subject_changed + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(marieCr), newSubject);
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(paulineCr), newSubject);
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(laureCr), newSubject);
linphone_core_set_network_reachable(pauline->lc, FALSE);
wait_for_list(coresList, &dummy, 1, 1000);
// Marie now changes the subject
newSubject = "Let's go drink a beer";
linphone_chat_room_set_subject(marieCr, newSubject);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_subject_changed,
initialMarieStats.number_of_subject_changed + 2, liblinphone_tester_sip_timeout));
BC_ASSERT_FALSE(wait_for_list(coresList, &pauline->stat.number_of_subject_changed,
initialPaulineStats.number_of_subject_changed + 2, 3000));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_subject_changed,
initialLaureStats.number_of_subject_changed + 2, liblinphone_tester_sip_timeout));
3221322232233224322532263227322832293230323132323233323432353236323732383239324032413242324332443245324632473248324932503251325232533254325532563257325832593260326132623263326432653266326732683269327032713272327332743275327632773278327932803281328232833284328532863287328832893290
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(marieCr), newSubject);
BC_ASSERT_STRING_NOT_EQUAL(linphone_chat_room_get_subject(paulineCr), newSubject);
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(laureCr), newSubject);
linphone_core_set_network_reachable(pauline->lc, TRUE);
wait_for_list(coresList, &dummy, 1, 1000);
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_subject_changed,
initialPaulineStats.number_of_subject_changed + 2, liblinphone_tester_sip_timeout));
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(paulineCr), newSubject);
// Test with more than one missed notify
linphone_core_set_network_reachable(pauline->lc, FALSE);
wait_for_list(coresList, &dummy, 1, 1000);
// Marie now changes the subject
newSubject = "Let's go drink a mineral water !";
linphone_chat_room_set_subject(marieCr, newSubject);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_subject_changed,
initialMarieStats.number_of_subject_changed + 3, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_subject_changed,
initialLaureStats.number_of_subject_changed + 3, liblinphone_tester_sip_timeout));
BC_ASSERT_FALSE(wait_for_list(coresList, &pauline->stat.number_of_subject_changed,
initialPaulineStats.number_of_subject_changed + 3, 3000));
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(marieCr), newSubject);
BC_ASSERT_STRING_NOT_EQUAL(linphone_chat_room_get_subject(paulineCr), newSubject);
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(laureCr), newSubject);
// Marie designates Laure as admin
LinphoneAddress *laureAddr = linphone_address_new(linphone_core_get_identity(laure->lc));
LinphoneParticipant *laureParticipant = linphone_chat_room_find_participant(marieCr, laureAddr);
LinphoneParticipant *laureParticipantFromPauline = linphone_chat_room_find_participant(paulineCr, laureAddr);
linphone_address_unref(laureAddr);
BC_ASSERT_PTR_NOT_NULL(laureParticipant);
BC_ASSERT_PTR_NOT_NULL(laureParticipantFromPauline);
linphone_chat_room_set_participant_admin_status(marieCr, laureParticipant, TRUE);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_participant_admin_statuses_changed,
initialMarieStats.number_of_participant_admin_statuses_changed + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_FALSE(wait_for_list(coresList, &pauline->stat.number_of_participant_admin_statuses_changed,
initialPaulineStats.number_of_participant_admin_statuses_changed + 1, 3000));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_participant_admin_statuses_changed,
initialLaureStats.number_of_participant_admin_statuses_changed + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(linphone_participant_is_admin(laureParticipant));
BC_ASSERT_FALSE(linphone_participant_is_admin(laureParticipantFromPauline));
linphone_core_set_network_reachable(pauline->lc, TRUE);
wait_for_list(coresList, &dummy, 1, 1000);
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_subject_changed,
initialPaulineStats.number_of_subject_changed + 3, liblinphone_tester_sip_timeout));
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(paulineCr), newSubject);
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_participant_admin_statuses_changed,
initialPaulineStats.number_of_participant_admin_statuses_changed + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(linphone_participant_is_admin(laureParticipantFromPauline));
// Test with a participant being removed
linphone_core_set_network_reachable(pauline->lc, FALSE);
wait_for_list(coresList, &dummy, 1, 1000);
// Laure leaves the room
linphone_chat_room_leave(laureCr);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_participants_removed,
initialMarieStats.number_of_participants_removed + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_FALSE(wait_for_list(coresList, &pauline->stat.number_of_participants_removed,
initialPaulineStats.number_of_participants_removed + 1, 3000));
3291329232933294329532963297329832993300330133023303330433053306330733083309331033113312331333143315331633173318331933203321332233233324332533263327332833293330333133323333333433353336333733383339334033413342334333443345334633473348334933503351335233533354335533563357335833593360
linphone_core_set_network_reachable(pauline->lc, TRUE);
wait_for_list(coresList, &dummy, 1, 1000);
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_participants_removed,
initialPaulineStats.number_of_participants_removed + 1,
liblinphone_tester_sip_timeout));
// Clean db from chat room
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
linphone_core_manager_delete_chat_room(laure, laureCr, coresList);
linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
linphone_core_manager_destroy(laure);
}
static void group_chat_room_notify_after_core_restart(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *laure = linphone_core_manager_create("laure_tcp_rc");
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
coresManagerList = bctbx_list_append(coresManagerList, laure);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(laure->lc)));
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
stats initialLaureStats = laure->stat;
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
LinphoneChatRoom *marieCr =
create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject, FALSE,
LinphoneChatRoomEphemeralModeDeviceManaged);
BC_ASSERT_PTR_NOT_NULL(marieCr);
participantsAddresses = NULL;
const LinphoneAddress *confAddr = linphone_chat_room_get_conference_address(marieCr);
// Check that the chat room is correctly created on Pauline's side and that the participants are added
LinphoneChatRoom *paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats,
confAddr, initialSubject, 2, FALSE);
BC_ASSERT_PTR_NOT_NULL(paulineCr);
// Check that the chat room is correctly created on Laure's side and that the participants are added
LinphoneChatRoom *laureCr =
check_creation_chat_room_client_side(coresList, laure, &initialLaureStats, confAddr, initialSubject, 2, FALSE);
BC_ASSERT_PTR_NOT_NULL(laureCr);
// Now paulines stops it's Core
coresList = bctbx_list_remove(coresList, pauline->lc);
// Make sure gruu is preserved
const char *uuid =
bctbx_strdup(linphone_config_get_string(linphone_core_get_config(pauline->lc), "misc", "uuid", NULL));
linphone_core_set_network_reachable(pauline->lc, FALSE); // to avoid unregister
linphone_core_manager_stop(pauline);
// Marie changes the subject
const char *newSubject = "New subject";
linphone_chat_room_set_subject(marieCr, newSubject);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_subject_changed,
3361336233633364336533663367336833693370337133723373337433753376337733783379338033813382338333843385338633873388338933903391339233933394339533963397339833993400340134023403340434053406340734083409341034113412341334143415341634173418341934203421342234233424342534263427342834293430
initialMarieStats.number_of_subject_changed + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_subject_changed,
initialLaureStats.number_of_subject_changed + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(marieCr), newSubject);
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(laureCr), newSubject);
// Laure leaves the room
linphone_chat_room_leave(laureCr);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_participants_removed,
initialMarieStats.number_of_participants_removed + 1, liblinphone_tester_sip_timeout));
// Pauline comes back
linphone_core_manager_reinit(pauline);
coresList = bctbx_list_append(coresList, pauline->lc);
// Make sure gruu is restored
linphone_config_set_string(linphone_core_get_config(pauline->lc), "misc", "uuid", uuid);
bctbx_list_t *tmpCoresManagerList = bctbx_list_append(NULL, pauline);
init_core_for_conference(tmpCoresManagerList);
bctbx_list_free(tmpCoresManagerList);
// Paulines starts it's Core again
linphone_core_manager_start(pauline, TRUE);
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_participants_removed,
initialPaulineStats.number_of_participants_removed + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_subject_changed,
initialPaulineStats.number_of_subject_changed + 1, 3000));
char *deviceIdentity = linphone_core_get_device_identity(pauline->lc);
LinphoneAddress *localAddr = linphone_address_new(deviceIdentity);
bctbx_free(deviceIdentity);
paulineCr = linphone_core_find_chat_room(pauline->lc, confAddr, localAddr);
linphone_address_unref(localAddr);
BC_ASSERT_PTR_NOT_NULL(paulineCr);
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(paulineCr), newSubject);
// Clean db from chat room
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
linphone_core_manager_delete_chat_room(laure, laureCr, coresList);
linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
linphone_core_manager_destroy(laure);
}
static void group_chat_room_send_refer_to_all_devices(void) {
LinphoneCoreManager *marie1 = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *marie2 = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline1 = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *pauline2 = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *laure = linphone_core_manager_create("laure_tcp_rc");
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie1);
coresManagerList = bctbx_list_append(coresManagerList, marie2);
coresManagerList = bctbx_list_append(coresManagerList, pauline1);
coresManagerList = bctbx_list_append(coresManagerList, pauline2);
coresManagerList = bctbx_list_append(coresManagerList, laure);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline1->lc)));
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(laure->lc)));
3431343234333434343534363437343834393440344134423443344434453446344734483449345034513452345334543455345634573458345934603461346234633464346534663467346834693470347134723473347434753476347734783479348034813482348334843485348634873488348934903491349234933494349534963497349834993500
stats initialMarie1Stats = marie1->stat;
stats initialMarie2Stats = marie2->stat;
stats initialPauline1Stats = pauline1->stat;
stats initialPauline2Stats = pauline2->stat;
stats initialLaureStats = laure->stat;
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
LinphoneChatRoom *marieCr =
create_chat_room_client_side(coresList, marie1, &initialMarie1Stats, participantsAddresses, initialSubject,
FALSE, LinphoneChatRoomEphemeralModeDeviceManaged);
participantsAddresses = NULL;
const LinphoneAddress *confAddr = linphone_chat_room_get_conference_address(marieCr);
// Check that the chat room is correctly created on second Marie's device
LinphoneChatRoom *marieCr2 =
check_creation_chat_room_client_side(coresList, marie2, &initialMarie2Stats, confAddr, initialSubject, 2, TRUE);
// Check that the chat room is correctly created on Pauline's side and that the participants are added
LinphoneChatRoom *paulineCr = check_creation_chat_room_client_side(coresList, pauline1, &initialPauline1Stats,
confAddr, initialSubject, 2, FALSE);
LinphoneChatRoom *paulineCr2 = check_creation_chat_room_client_side(coresList, pauline2, &initialPauline2Stats,
confAddr, initialSubject, 2, FALSE);
// Check that the chat room is correctly created on Laure's side and that the participants are added
LinphoneChatRoom *laureCr =
check_creation_chat_room_client_side(coresList, laure, &initialLaureStats, confAddr, initialSubject, 2, FALSE);
// Check that added Marie's device didn't change her admin status
LinphoneAddress *marieAddr = linphone_address_new(linphone_core_get_identity(marie1->lc));
LinphoneParticipant *marieParticipant = linphone_chat_room_get_me(marieCr);
if (BC_ASSERT_PTR_NOT_NULL(marieParticipant)) BC_ASSERT_TRUE(linphone_participant_is_admin(marieParticipant));
marieParticipant = linphone_chat_room_get_me(marieCr2);
if (BC_ASSERT_PTR_NOT_NULL(marieParticipant)) BC_ASSERT_TRUE(linphone_participant_is_admin(marieParticipant));
marieParticipant = linphone_chat_room_find_participant(paulineCr, marieAddr);
if (BC_ASSERT_PTR_NOT_NULL(marieParticipant)) BC_ASSERT_TRUE(linphone_participant_is_admin(marieParticipant));
marieParticipant = linphone_chat_room_find_participant(paulineCr2, marieAddr);
if (BC_ASSERT_PTR_NOT_NULL(marieParticipant)) BC_ASSERT_TRUE(linphone_participant_is_admin(marieParticipant));
marieParticipant = linphone_chat_room_find_participant(laureCr, marieAddr);
if (BC_ASSERT_PTR_NOT_NULL(marieParticipant)) BC_ASSERT_TRUE(linphone_participant_is_admin(marieParticipant));
linphone_address_unref(marieAddr);
// Marie removes Laure from the chat room
LinphoneAddress *laureAddr = linphone_address_new(linphone_core_get_identity(laure->lc));
LinphoneParticipant *laureParticipant = linphone_chat_room_find_participant(marieCr, laureAddr);
linphone_address_unref(laureAddr);
BC_ASSERT_PTR_NOT_NULL(laureParticipant);
linphone_chat_room_remove_participant(marieCr, laureParticipant);
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_LinphoneConferenceStateTerminated,
initialLaureStats.number_of_LinphoneConferenceStateTerminated + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &marie1->stat.number_of_participants_removed,
initialMarie1Stats.number_of_participants_removed + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &marie2->stat.number_of_participants_removed,
initialMarie2Stats.number_of_participants_removed + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline1->stat.number_of_participants_removed,
initialPauline1Stats.number_of_participants_removed + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline2->stat.number_of_participants_removed,
initialPauline2Stats.number_of_participants_removed + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(marieCr), 1, int, "%d");
3501350235033504350535063507350835093510351135123513351435153516351735183519352035213522352335243525352635273528352935303531353235333534353535363537353835393540354135423543354435453546354735483549355035513552355335543555355635573558355935603561356235633564356535663567356835693570
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(paulineCr), 1, int, "%d");
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(paulineCr2), 1, int, "%d");
// Clean db from chat room
linphone_core_manager_delete_chat_room(marie1, marieCr, coresList);
linphone_core_delete_chat_room(marie2->lc, marieCr2);
linphone_core_manager_delete_chat_room(laure, laureCr, coresList);
linphone_core_manager_delete_chat_room(pauline1, paulineCr, coresList);
linphone_core_delete_chat_room(pauline2->lc, paulineCr2);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie1);
linphone_core_manager_destroy(marie2);
linphone_core_manager_destroy(pauline1);
linphone_core_manager_destroy(pauline2);
linphone_core_manager_destroy(laure);
}
static void group_chat_room_add_device(void) {
LinphoneCoreManager *marie1 = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline1 = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *pauline2 = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *laure = linphone_core_manager_create("laure_tcp_rc");
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie1);
coresManagerList = bctbx_list_append(coresManagerList, pauline1);
coresManagerList = bctbx_list_append(coresManagerList, pauline2);
coresManagerList = bctbx_list_append(coresManagerList, laure);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline1->lc)));
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(laure->lc)));
stats initialMarie1Stats = marie1->stat;
stats initialPauline1Stats = pauline1->stat;
stats initialPauline2Stats = pauline2->stat;
stats initialLaureStats = laure->stat;
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
LinphoneChatRoom *marieCr =
create_chat_room_client_side(coresList, marie1, &initialMarie1Stats, participantsAddresses, initialSubject,
FALSE, LinphoneChatRoomEphemeralModeDeviceManaged);
participantsAddresses = NULL;
const LinphoneAddress *confAddr = linphone_chat_room_get_conference_address(marieCr);
// Check that the chat room is correctly created on Pauline's side and that the participants are added
LinphoneChatRoom *paulineCr = check_creation_chat_room_client_side(coresList, pauline1, &initialPauline1Stats,
confAddr, initialSubject, 2, FALSE);
LinphoneChatRoom *paulineCr2 = check_creation_chat_room_client_side(coresList, pauline2, &initialPauline2Stats,
confAddr, initialSubject, 2, FALSE);
// Check that the chat room is correctly created on Laure's side and that the participants are added
LinphoneChatRoom *laureCr =
check_creation_chat_room_client_side(coresList, laure, &initialLaureStats, confAddr, initialSubject, 2, FALSE);
// Marie adds a new device
LinphoneCoreManager *marie2 = linphone_core_manager_create("marie_rc");
coresManagerList = bctbx_list_append(coresManagerList, marie2);
LinphoneAddress *factoryAddr = linphone_address_new(sFactoryUri);
_configure_core_for_conference(marie2, factoryAddr);
linphone_address_unref(factoryAddr);
LinphoneCoreCbs *cbs = linphone_factory_create_core_cbs(linphone_factory_get());
linphone_core_cbs_set_chat_room_state_changed(cbs, core_chat_room_state_changed);
configure_core_for_callbacks(marie2, cbs);
linphone_core_cbs_unref(cbs);
coresList = bctbx_list_append(coresList, marie2->lc);
3571357235733574357535763577357835793580358135823583358435853586358735883589359035913592359335943595359635973598359936003601360236033604360536063607360836093610361136123613361436153616361736183619362036213622362336243625362636273628362936303631363236333634363536363637363836393640
stats initialMarie2Stats = marie2->stat;
_start_core(marie2);
// Check that the chat room is correctly created on second Marie's device
LinphoneChatRoom *marieCr2 =
check_creation_chat_room_client_side(coresList, marie2, &initialMarie2Stats, confAddr, initialSubject, 2, TRUE);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie1->stat.number_of_participant_devices_added,
initialMarie1Stats.number_of_participant_devices_added + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline1->stat.number_of_participant_devices_added,
initialMarie1Stats.number_of_participant_devices_added + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline2->stat.number_of_participant_devices_added,
initialMarie1Stats.number_of_participant_devices_added + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_participant_devices_added,
initialMarie1Stats.number_of_participant_devices_added + 1,
liblinphone_tester_sip_timeout));
// Check that adding Marie's device didn't change her admin status
LinphoneParticipant *marieParticipant = linphone_chat_room_get_me(marieCr);
BC_ASSERT_PTR_NOT_NULL(marieParticipant);
BC_ASSERT_TRUE(linphone_participant_is_admin(marieParticipant));
marieParticipant = linphone_chat_room_get_me(marieCr2);
BC_ASSERT_PTR_NOT_NULL(marieParticipant);
BC_ASSERT_TRUE(linphone_participant_is_admin(marieParticipant));
LinphoneAddress *marieAddr = linphone_address_new(linphone_core_get_identity(marie1->lc));
marieParticipant = linphone_chat_room_find_participant(paulineCr, marieAddr);
BC_ASSERT_PTR_NOT_NULL(marieParticipant);
BC_ASSERT_TRUE(linphone_participant_is_admin(marieParticipant));
marieParticipant = linphone_chat_room_find_participant(paulineCr2, marieAddr);
BC_ASSERT_PTR_NOT_NULL(marieParticipant);
BC_ASSERT_TRUE(linphone_participant_is_admin(marieParticipant));
marieParticipant = linphone_chat_room_find_participant(laureCr, marieAddr);
BC_ASSERT_PTR_NOT_NULL(marieParticipant);
BC_ASSERT_TRUE(linphone_participant_is_admin(marieParticipant));
linphone_address_unref(marieAddr);
// Marie removes Laure from the chat room
LinphoneAddress *laureAddr = linphone_address_new(linphone_core_get_identity(laure->lc));
LinphoneParticipant *laureParticipant = linphone_chat_room_find_participant(marieCr, laureAddr);
linphone_address_unref(laureAddr);
BC_ASSERT_PTR_NOT_NULL(laureParticipant);
linphone_chat_room_remove_participant(marieCr, laureParticipant);
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_LinphoneConferenceStateTerminated,
initialLaureStats.number_of_LinphoneConferenceStateTerminated + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &marie1->stat.number_of_participants_removed,
initialMarie1Stats.number_of_participants_removed + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &marie2->stat.number_of_participants_removed,
initialMarie2Stats.number_of_participants_removed + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline1->stat.number_of_participants_removed,
initialPauline1Stats.number_of_participants_removed + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline2->stat.number_of_participants_removed,
initialPauline2Stats.number_of_participants_removed + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(marieCr), 1, int, "%d");
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(paulineCr), 1, int, "%d");
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(paulineCr2), 1, int, "%d");
// Clean db from chat room
linphone_core_manager_delete_chat_room(marie1, marieCr, coresList);
linphone_core_delete_chat_room(marie2->lc, marieCr2);
linphone_core_manager_delete_chat_room(laure, laureCr, coresList);
linphone_core_manager_delete_chat_room(pauline1, paulineCr, coresList);
linphone_core_delete_chat_room(pauline2->lc, paulineCr2);
3641364236433644364536463647364836493650365136523653365436553656365736583659366036613662366336643665366636673668366936703671367236733674367536763677367836793680368136823683368436853686368736883689369036913692369336943695369636973698369937003701370237033704370537063707370837093710
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie1);
linphone_core_manager_destroy(marie2);
linphone_core_manager_destroy(pauline1);
linphone_core_manager_destroy(pauline2);
linphone_core_manager_destroy(laure);
}
static void multiple_is_composing_notification(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *laure = linphone_core_manager_create("laure_tcp_rc");
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
const bctbx_list_t *composing_addresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
coresManagerList = bctbx_list_append(coresManagerList, laure);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(laure->lc)));
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
stats initialLaureStats = laure->stat;
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
LinphoneChatRoom *marieCr =
create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject, FALSE,
LinphoneChatRoomEphemeralModeDeviceManaged);
participantsAddresses = NULL;
const LinphoneAddress *confAddr = linphone_chat_room_get_conference_address(marieCr);
// Check that the chat room is correctly created on Pauline's side and that the participants are added
LinphoneChatRoom *paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats,
confAddr, initialSubject, 2, FALSE);
// Check that the chat room is correctly created on Laure's side and that the participants are added
LinphoneChatRoom *laureCr =
check_creation_chat_room_client_side(coresList, laure, &initialLaureStats, confAddr, initialSubject, 2, FALSE);
// Only one is composing
linphone_chat_room_compose(paulineCr);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneIsComposingActiveReceived, 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_LinphoneIsComposingActiveReceived, 1,
liblinphone_tester_sip_timeout));
// Laure side
composing_addresses = linphone_chat_room_get_composing_addresses(laureCr);
BC_ASSERT_EQUAL((int)bctbx_list_size(composing_addresses), 1, int, "%i");
if (bctbx_list_size(composing_addresses) == 1) {
LinphoneAddress *addr = (LinphoneAddress *)bctbx_list_get_data(composing_addresses);
BC_ASSERT_STRING_EQUAL(linphone_address_get_username(addr), linphone_address_get_username(pauline->identity));
}
// Marie side
composing_addresses = linphone_chat_room_get_composing_addresses(marieCr);
BC_ASSERT_EQUAL((int)bctbx_list_size(composing_addresses), 1, int, "%i");
if (bctbx_list_size(composing_addresses) == 1) {
LinphoneAddress *addr = (LinphoneAddress *)bctbx_list_get_data(composing_addresses);
BC_ASSERT_STRING_EQUAL(linphone_address_get_username(addr), linphone_address_get_username(pauline->identity));
}
// Pauline side
3711371237133714371537163717371837193720372137223723372437253726372737283729373037313732373337343735373637373738373937403741374237433744374537463747374837493750375137523753375437553756375737583759376037613762376337643765376637673768376937703771377237733774377537763777377837793780
composing_addresses = linphone_chat_room_get_composing_addresses(paulineCr);
BC_ASSERT_EQUAL((int)bctbx_list_size(composing_addresses), 0, int, "%i");
wait_for_list(coresList, 0, 1, 1500);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneIsComposingIdleReceived, 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_LinphoneIsComposingIdleReceived, 1,
liblinphone_tester_sip_timeout));
composing_addresses = linphone_chat_room_get_composing_addresses(marieCr);
BC_ASSERT_EQUAL((int)bctbx_list_size(composing_addresses), 0, int, "%i");
composing_addresses = linphone_chat_room_get_composing_addresses(laureCr);
BC_ASSERT_EQUAL((int)bctbx_list_size(composing_addresses), 0, int, "%i");
// multiple is composing
linphone_chat_room_compose(paulineCr);
linphone_chat_room_compose(marieCr);
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_LinphoneIsComposingActiveReceived, 3,
liblinphone_tester_sip_timeout)); // + 2
// Laure side
composing_addresses = linphone_chat_room_get_composing_addresses(laureCr);
BC_ASSERT_EQUAL((int)bctbx_list_size(composing_addresses), 2, int, "%i");
if (bctbx_list_size(composing_addresses) == 2) {
while (composing_addresses) {
LinphoneAddress *addr = (LinphoneAddress *)bctbx_list_get_data(composing_addresses);
bool_t equal =
strcmp(linphone_address_get_username(addr), linphone_address_get_username(pauline->identity)) == 0 ||
strcmp(linphone_address_get_username(addr), linphone_address_get_username(marie->identity)) == 0;
BC_ASSERT_TRUE(equal);
composing_addresses = bctbx_list_next(composing_addresses);
}
}
// Marie side
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneIsComposingActiveReceived, 2,
liblinphone_tester_sip_timeout)); // + 1
composing_addresses = linphone_chat_room_get_composing_addresses(marieCr);
BC_ASSERT_EQUAL((int)bctbx_list_size(composing_addresses), 1, int, "%i");
if (bctbx_list_size(composing_addresses) == 1) {
LinphoneAddress *addr = (LinphoneAddress *)bctbx_list_get_data(composing_addresses);
BC_ASSERT_STRING_EQUAL(linphone_address_get_username(addr), linphone_address_get_username(pauline->identity));
}
// Pauline side
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneIsComposingActiveReceived, 1, 2000));
composing_addresses = linphone_chat_room_get_composing_addresses(paulineCr);
BC_ASSERT_EQUAL((int)bctbx_list_size(composing_addresses), 1, int, "%i");
if (bctbx_list_size(composing_addresses) == 1) {
LinphoneAddress *addr = (LinphoneAddress *)bctbx_list_get_data(composing_addresses);
BC_ASSERT_STRING_EQUAL(linphone_address_get_username(addr), linphone_address_get_username(marie->identity));
}
wait_for_list(coresList, 0, 1, 1500);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneIsComposingIdleReceived, 2,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_LinphoneIsComposingIdleReceived, 3,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneIsComposingIdleReceived, 1,
liblinphone_tester_sip_timeout));
composing_addresses = linphone_chat_room_get_composing_addresses(marieCr);
BC_ASSERT_EQUAL((int)bctbx_list_size(composing_addresses), 0, int, "%i");
composing_addresses = linphone_chat_room_get_composing_addresses(laureCr);
BC_ASSERT_EQUAL((int)bctbx_list_size(composing_addresses), 0, int, "%i");
composing_addresses = linphone_chat_room_get_composing_addresses(paulineCr);
BC_ASSERT_EQUAL((int)bctbx_list_size(composing_addresses), 0, int, "%i");
// Clean db from chat room
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
3781378237833784378537863787378837893790379137923793379437953796379737983799380038013802380338043805380638073808380938103811381238133814381538163817381838193820382138223823382438253826382738283829383038313832383338343835383638373838383938403841384238433844384538463847384838493850
linphone_core_manager_delete_chat_room(laure, laureCr, coresList);
linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
linphone_core_manager_destroy(laure);
}
static void group_chat_room_fallback_to_basic_chat_room(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
linphone_core_remove_linphone_spec(pauline->lc, "groupchat");
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
// Marie creates a new group chat room
LinphoneChatRoom *marieCr = linphone_core_create_client_group_chat_room(marie->lc, "Fallback", TRUE);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneConferenceStateInstantiated,
initialMarieStats.number_of_LinphoneConferenceStateInstantiated + 1, 100));
// Add participants
linphone_chat_room_add_participants(marieCr, participantsAddresses);
// Check that the group chat room creation fails and that a fallback to a basic chat room is done
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneConferenceStateCreationPending,
initialMarieStats.number_of_LinphoneConferenceStateCreationPending + 1, 10000));
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneConferenceStateCreated,
initialMarieStats.number_of_LinphoneConferenceStateCreated + 1, 10000));
BC_ASSERT_EQUAL(marie->stat.number_of_LinphoneConferenceStateCreationFailed,
initialMarieStats.number_of_LinphoneConferenceStateCreationFailed, int, "%d");
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(marieCr), 1, int, "%d");
BC_ASSERT_TRUE(linphone_chat_room_get_capabilities(marieCr) & LinphoneChatRoomCapabilitiesBasic);
bctbx_list_free_with_data(participantsAddresses, (bctbx_list_free_func)linphone_address_unref);
participantsAddresses = NULL;
// Send a message and check that a basic chat room is created on Pauline's side
LinphoneChatMessage *msg = linphone_chat_room_create_message_from_utf8(marieCr, "Hey Pauline!");
linphone_chat_message_send(msg);
linphone_chat_message_unref(msg);
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageReceived,
initialPaulineStats.number_of_LinphoneMessageReceived + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_PTR_NOT_NULL(pauline->stat.last_received_chat_message);
if (pauline->stat.last_received_chat_message)
BC_ASSERT_STRING_EQUAL(linphone_chat_message_get_content_type(pauline->stat.last_received_chat_message),
"text/plain");
LinphoneChatRoom *paulineCr =
linphone_core_get_chat_room(pauline->lc, linphone_chat_room_get_local_address(marieCr));
BC_ASSERT_PTR_NOT_NULL(paulineCr);
if (paulineCr) BC_ASSERT_TRUE(linphone_chat_room_get_capabilities(paulineCr) & LinphoneChatRoomCapabilitiesBasic);
// Clean db from chat room
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
}
3851385238533854385538563857385838593860386138623863386438653866386738683869387038713872387338743875387638773878387938803881388238833884388538863887388838893890389138923893389438953896389738983899390039013902390339043905390639073908390939103911391239133914391539163917391839193920
static void group_chat_room_creation_fails_if_invited_participants_dont_support_it(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *laure = linphone_core_manager_create("laure_tcp_rc");
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
coresManagerList = bctbx_list_append(coresManagerList, laure);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
linphone_core_remove_linphone_spec(pauline->lc, "groupchat");
linphone_core_remove_linphone_spec(laure->lc, "groupchat");
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(laure->lc)));
stats initialMarieStats = marie->stat;
// Marie creates a new group chat room
LinphoneChatRoom *marieCr = linphone_core_create_client_group_chat_room(marie->lc, "Hello there", FALSE);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneConferenceStateInstantiated,
initialMarieStats.number_of_LinphoneConferenceStateInstantiated + 1, 100));
// Add participants
linphone_chat_room_add_participants(marieCr, participantsAddresses);
// Check that the group chat room creation fails
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneConferenceStateCreationPending,
initialMarieStats.number_of_LinphoneConferenceStateCreationPending + 1, 10000));
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneConferenceStateCreationFailed,
initialMarieStats.number_of_LinphoneConferenceStateCreationFailed + 1, 10000));
bctbx_list_free_with_data(participantsAddresses, (bctbx_list_free_func)linphone_address_unref);
participantsAddresses = NULL;
BC_ASSERT_EQUAL(linphone_chat_room_get_state(marieCr), LinphoneConferenceStateCreationFailed, int, "%d");
// Clean db from chat room
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
linphone_core_manager_destroy(laure);
}
static void group_chat_room_creation_successful_if_at_least_one_invited_participant_supports_it(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *laure = linphone_core_manager_create("laure_tcp_rc");
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
coresManagerList = bctbx_list_append(coresManagerList, laure);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
linphone_core_remove_linphone_spec(laure->lc, "groupchat");
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(laure->lc)));
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
stats initialLaureStats = laure->stat;
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
LinphoneChatRoom *marieCr = create_chat_room_client_side_with_expected_number_of_participants(
3921392239233924392539263927392839293930393139323933393439353936393739383939394039413942394339443945394639473948394939503951395239533954395539563957395839593960396139623963396439653966396739683969397039713972397339743975397639773978397939803981398239833984398539863987398839893990
coresList, marie, &initialMarieStats, participantsAddresses, initialSubject, 1, FALSE,
LinphoneChatRoomEphemeralModeDeviceManaged);
participantsAddresses = NULL;
const LinphoneAddress *confAddr = linphone_chat_room_get_conference_address(marieCr);
// Check that the chat room is correctly created on Pauline's side and that the participants are added
LinphoneChatRoom *paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats,
confAddr, initialSubject, 1, FALSE);
// Check that the chat room has not been created on Laure's side
BC_ASSERT_EQUAL(initialLaureStats.number_of_LinphoneConferenceStateCreated,
laure->stat.number_of_LinphoneConferenceStateCreated, int, "%d");
// Clean db from chat room
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
linphone_core_manager_destroy(laure);
}
static void group_chat_room_migrate_from_basic_chat_room(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
bctbx_list_t *coresManagerList = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
// Enable migration mecanism only for marie and create a basic chat room
LinphoneAddress *paulineAddr = linphone_address_new(linphone_core_get_identity(pauline->lc));
linphone_core_remove_linphone_spec(marie->lc, "groupchat"); // Prevent basic chat room from migrating directly
linphone_config_set_int(linphone_core_get_config(marie->lc), "misc",
"enable_basic_to_client_group_chat_room_migration", 1);
LinphoneChatRoom *marieCr = linphone_core_get_chat_room(marie->lc, paulineAddr);
BC_ASSERT_TRUE(linphone_chat_room_get_capabilities(marieCr) & (LinphoneChatRoomCapabilitiesMigratable));
// Send a message and check that a basic chat room is created on Pauline's side
LinphoneChatMessage *msg = linphone_chat_room_create_message_from_utf8(marieCr, "Hey Pauline!");
linphone_chat_message_send(msg);
linphone_chat_message_unref(msg);
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageReceived,
initialPaulineStats.number_of_LinphoneMessageReceived + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_PTR_NOT_NULL(pauline->stat.last_received_chat_message);
if (pauline->stat.last_received_chat_message)
BC_ASSERT_STRING_EQUAL(linphone_chat_message_get_content_type(pauline->stat.last_received_chat_message),
"text/plain");
linphone_config_set_int(linphone_core_get_config(pauline->lc), "misc",
"enable_basic_to_client_group_chat_room_migration", 1);
LinphoneChatRoom *paulineCr =
linphone_core_get_chat_room(pauline->lc, linphone_chat_room_get_local_address(marieCr));
BC_ASSERT_PTR_NOT_NULL(paulineCr);
if (paulineCr) {
BC_ASSERT_TRUE(linphone_chat_room_get_capabilities(paulineCr) &
(LinphoneChatRoomCapabilitiesBasic | LinphoneChatRoomCapabilitiesMigratable));
}
// Enable chat room migration and restart core for Marie
_linphone_chat_room_enable_migration(marieCr, TRUE); // Will add Migratable capability to the in-db chatroom
coresList = bctbx_list_remove(coresList, marie->lc);
linphone_core_manager_reinit(marie);
bctbx_list_t *tmpCoresManagerList = bctbx_list_append(NULL, marie);
bctbx_list_t *tmpCoresList = init_core_for_conference(tmpCoresManagerList);
3991399239933994399539963997399839994000400140024003400440054006400740084009401040114012401340144015401640174018401940204021402240234024402540264027402840294030403140324033403440354036403740384039404040414042404340444045404640474048404940504051405240534054405540564057405840594060
bctbx_list_free(tmpCoresManagerList);
coresList = bctbx_list_concat(coresList, tmpCoresList);
linphone_config_set_int(linphone_core_get_config(marie->lc), "misc",
"enable_basic_to_client_group_chat_room_migration", 1);
linphone_core_manager_start(marie, TRUE);
marieCr = linphone_core_get_chat_room(marie->lc, paulineAddr);
/* // Enable chat room migration and restart core for Pauline */
_linphone_chat_room_enable_migration(paulineCr, TRUE);
coresList = bctbx_list_remove(coresList, pauline->lc);
linphone_core_manager_reinit(pauline);
tmpCoresManagerList = bctbx_list_append(NULL, pauline);
tmpCoresList = init_core_for_conference(tmpCoresManagerList);
bctbx_list_free(tmpCoresManagerList);
coresList = bctbx_list_concat(coresList, tmpCoresList);
linphone_config_set_int(linphone_core_get_config(pauline->lc), "misc",
"enable_basic_to_client_group_chat_room_migration", 1);
linphone_core_manager_start(pauline, TRUE);
paulineCr = linphone_core_get_chat_room(pauline->lc, linphone_chat_room_get_local_address(marieCr));
// Send a new message to initiate chat room migration
BC_ASSERT_PTR_NOT_NULL(marieCr);
BC_ASSERT_PTR_NOT_NULL(paulineCr);
if (marieCr && paulineCr) {
initialMarieStats = marie->stat;
initialPaulineStats = pauline->stat;
linphone_core_add_linphone_spec(marie->lc, "groupchat"); // Enable migration now
BC_ASSERT_EQUAL(linphone_chat_room_get_capabilities(marieCr),
LinphoneChatRoomCapabilitiesBasic | LinphoneChatRoomCapabilitiesProxy |
LinphoneChatRoomCapabilitiesMigratable | LinphoneChatRoomCapabilitiesOneToOne,
int, "%d");
msg = linphone_chat_room_create_message_from_utf8(marieCr, "Did you migrate?");
linphone_chat_message_send(msg);
linphone_chat_message_unref(msg);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneConferenceStateCreationPending,
initialMarieStats.number_of_LinphoneConferenceStateCreationPending + 1, 10000));
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneConferenceStateCreated,
initialMarieStats.number_of_LinphoneConferenceStateCreated + 1, 10000));
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneChatRoomConferenceJoined,
initialMarieStats.number_of_LinphoneChatRoomConferenceJoined + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(linphone_chat_room_get_capabilities(marieCr) & LinphoneChatRoomCapabilitiesConference);
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(marieCr), 1, int, "%d");
BC_ASSERT_EQUAL(linphone_chat_room_get_history_size(marieCr), 2, int, "%d");
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneConferenceStateCreationPending,
initialPaulineStats.number_of_LinphoneConferenceStateCreationPending + 1, 10000));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneConferenceStateCreated,
initialPaulineStats.number_of_LinphoneConferenceStateCreated + 1, 10000));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneChatRoomConferenceJoined,
initialPaulineStats.number_of_LinphoneChatRoomConferenceJoined + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(linphone_chat_room_get_capabilities(paulineCr) & LinphoneChatRoomCapabilitiesConference);
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(paulineCr), 1, int, "%d");
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageReceived,
initialPaulineStats.number_of_LinphoneMessageReceived + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_EQUAL(linphone_chat_room_get_history_size(paulineCr), 2, int, "%d");
msg = linphone_chat_room_create_message_from_utf8(marieCr, "Let's go drink a beer");
linphone_chat_message_send(msg);
linphone_chat_message_unref(msg);
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageReceived,
initialPaulineStats.number_of_LinphoneMessageReceived + 2,
liblinphone_tester_sip_timeout));
BC_ASSERT_EQUAL(linphone_chat_room_get_history_size(marieCr), 3, int, "%d");
BC_ASSERT_EQUAL(linphone_chat_room_get_history_size(paulineCr), 3, int, "%d");
4061406240634064406540664067406840694070407140724073407440754076407740784079408040814082408340844085408640874088408940904091409240934094409540964097409840994100410141024103410441054106410741084109411041114112411341144115411641174118411941204121412241234124412541264127412841294130
msg = linphone_chat_room_create_message_from_utf8(paulineCr, "Let's go drink mineral water instead");
linphone_chat_message_send(msg);
linphone_chat_message_unref(msg);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneMessageReceived,
initialMarieStats.number_of_LinphoneMessageReceived + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_EQUAL(linphone_chat_room_get_history_size(marieCr), 4, int, "%d");
BC_ASSERT_EQUAL(linphone_chat_room_get_history_size(paulineCr), 4, int, "%d");
BC_ASSERT_EQUAL((int)bctbx_list_size(linphone_core_get_chat_rooms(marie->lc)), 1, int, "%d");
BC_ASSERT_EQUAL((int)bctbx_list_size(linphone_core_get_chat_rooms(pauline->lc)), 1, int, "%d");
}
// Clean db from chat room
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
linphone_address_unref(paulineAddr);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
}
static void group_chat_room_migrate_from_basic_to_client_fail(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
int dummy = 0;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
linphone_core_remove_linphone_spec(pauline->lc, "groupchat");
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
// Marie creates a new group chat room
LinphoneChatRoom *marieCr = linphone_core_create_client_group_chat_room(marie->lc, "Fallback", TRUE);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneConferenceStateInstantiated,
initialMarieStats.number_of_LinphoneConferenceStateInstantiated + 1, 100));
// Add participants
linphone_chat_room_add_participants(marieCr, participantsAddresses);
// Check that the group chat room creation fails and that a fallback to a basic chat room is done
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneConferenceStateCreationPending,
initialMarieStats.number_of_LinphoneConferenceStateCreationPending + 1, 10000));
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneConferenceStateCreated,
initialMarieStats.number_of_LinphoneConferenceStateCreated + 1, 10000));
BC_ASSERT_EQUAL(marie->stat.number_of_LinphoneConferenceStateCreationFailed,
initialMarieStats.number_of_LinphoneConferenceStateCreationFailed, int, "%d");
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(marieCr), 1, int, "%d");
BC_ASSERT_TRUE(linphone_chat_room_get_capabilities(marieCr) & LinphoneChatRoomCapabilitiesBasic);
bctbx_list_free_with_data(participantsAddresses, (bctbx_list_free_func)linphone_address_unref);
participantsAddresses = NULL;
// Send a message and check that a basic chat room is created on Pauline's side
LinphoneChatMessage *msg = linphone_chat_room_create_message_from_utf8(marieCr, "Hey Pauline!");
linphone_chat_message_send(msg);
linphone_chat_message_unref(msg);
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageReceived,
initialPaulineStats.number_of_LinphoneMessageReceived + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_PTR_NOT_NULL(pauline->stat.last_received_chat_message);
if (pauline->stat.last_received_chat_message)
BC_ASSERT_STRING_EQUAL(linphone_chat_message_get_content_type(pauline->stat.last_received_chat_message),
"text/plain");
4131413241334134413541364137413841394140414141424143414441454146414741484149415041514152415341544155415641574158415941604161416241634164416541664167416841694170417141724173417441754176417741784179418041814182418341844185418641874188418941904191419241934194419541964197419841994200
LinphoneChatRoom *paulineCr =
linphone_core_get_chat_room(pauline->lc, linphone_chat_room_get_local_address(marieCr));
BC_ASSERT_PTR_NOT_NULL(paulineCr);
if (paulineCr) BC_ASSERT_TRUE(linphone_chat_room_get_capabilities(paulineCr) & LinphoneChatRoomCapabilitiesBasic);
// Enable chat room migration and restart core for Marie
_linphone_chat_room_enable_migration(marieCr, TRUE);
if (marieCr) linphone_chat_room_unref(marieCr);
coresList = bctbx_list_remove(coresList, marie->lc);
linphone_core_manager_reinit(marie);
bctbx_list_t *tmpCoresManagerList = bctbx_list_append(NULL, marie);
bctbx_list_t *tmpCoresList = init_core_for_conference(tmpCoresManagerList);
bctbx_list_free(tmpCoresManagerList);
coresList = bctbx_list_concat(coresList, tmpCoresList);
// Send a new message to initiate chat room migration
linphone_config_set_int(linphone_core_get_config(marie->lc), "misc",
"enable_basic_to_client_group_chat_room_migration", 1);
linphone_config_set_int(linphone_core_get_config(marie->lc), "misc",
"basic_to_client_group_chat_room_migration_timer", 5);
linphone_core_manager_start(marie, TRUE);
LinphoneAddress *paulineAddr = linphone_address_new(linphone_core_get_identity(pauline->lc));
marieCr = linphone_core_get_chat_room(marie->lc, paulineAddr);
linphone_address_unref(paulineAddr);
paulineCr = linphone_core_get_chat_room(pauline->lc, linphone_chat_room_get_local_address(marieCr));
BC_ASSERT_PTR_NOT_NULL(marieCr);
BC_ASSERT_PTR_NOT_NULL(paulineCr);
if (marieCr && paulineCr) {
initialMarieStats = marie->stat;
initialPaulineStats = pauline->stat;
BC_ASSERT_EQUAL(linphone_chat_room_get_capabilities(marieCr),
LinphoneChatRoomCapabilitiesBasic | LinphoneChatRoomCapabilitiesProxy |
LinphoneChatRoomCapabilitiesMigratable | LinphoneChatRoomCapabilitiesOneToOne,
int, "%d");
msg = linphone_chat_room_create_message_from_utf8(marieCr, "Did you migrate?");
linphone_chat_message_send(msg);
linphone_chat_message_unref(msg);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneConferenceStateCreationPending,
initialMarieStats.number_of_LinphoneConferenceStateCreationPending + 1, 10000));
BC_ASSERT_FALSE(wait_for_list(coresList, &marie->stat.number_of_LinphoneConferenceStateCreated,
initialMarieStats.number_of_LinphoneConferenceStateCreated + 1, 10000));
BC_ASSERT_TRUE(linphone_chat_room_get_capabilities(marieCr) & LinphoneChatRoomCapabilitiesBasic);
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(marieCr), 1, int, "%d");
BC_ASSERT_EQUAL(linphone_chat_room_get_history_size(marieCr), 2, int, "%d");
BC_ASSERT_FALSE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneConferenceStateCreationPending,
initialPaulineStats.number_of_LinphoneConferenceStateCreationPending + 1, 10000));
BC_ASSERT_FALSE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneConferenceStateCreated,
initialPaulineStats.number_of_LinphoneConferenceStateCreated + 1, 10000));
BC_ASSERT_TRUE(linphone_chat_room_get_capabilities(paulineCr) & LinphoneChatRoomCapabilitiesBasic);
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(paulineCr), 1, int, "%d");
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageReceived,
initialPaulineStats.number_of_LinphoneMessageReceived + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_EQUAL(linphone_chat_room_get_history_size(paulineCr), 2, int, "%d");
msg = linphone_chat_room_create_message_from_utf8(marieCr, "Let's go drink a beer");
linphone_chat_message_send(msg);
linphone_chat_message_unref(msg);
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageReceived,
initialPaulineStats.number_of_LinphoneMessageReceived + 2,
liblinphone_tester_sip_timeout));
BC_ASSERT_EQUAL(linphone_chat_room_get_history_size(marieCr), 3, int, "%d");
BC_ASSERT_EQUAL(linphone_chat_room_get_history_size(paulineCr), 3, int, "%d");
msg = linphone_chat_room_create_message_from_utf8(paulineCr, "Let's go drink mineral water instead");
linphone_chat_message_send(msg);
linphone_chat_message_unref(msg);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneMessageReceived,
initialMarieStats.number_of_LinphoneMessageReceived + 1,
4201420242034204420542064207420842094210421142124213421442154216421742184219422042214222422342244225422642274228422942304231423242334234423542364237423842394240424142424243424442454246424742484249425042514252425342544255425642574258425942604261426242634264426542664267426842694270
liblinphone_tester_sip_timeout));
BC_ASSERT_EQUAL(linphone_chat_room_get_history_size(marieCr), 4, int, "%d");
BC_ASSERT_EQUAL(linphone_chat_room_get_history_size(paulineCr), 4, int, "%d");
// Activate groupchat on Pauline's side and wait for 5 seconds, the migration should now be done on next message
// sending
_linphone_chat_room_enable_migration(paulineCr, TRUE);
coresList = bctbx_list_remove(coresList, pauline->lc);
linphone_core_manager_reinit(pauline);
tmpCoresManagerList = bctbx_list_append(NULL, pauline);
tmpCoresList = init_core_for_conference(tmpCoresManagerList);
linphone_config_set_int(linphone_core_get_config(pauline->lc), "misc",
"enable_basic_to_client_group_chat_room_migration", 1);
linphone_core_add_linphone_spec(pauline->lc, "groupchat");
bctbx_list_free(tmpCoresManagerList);
coresList = bctbx_list_concat(coresList, tmpCoresList);
linphone_core_manager_start(pauline, TRUE);
paulineCr = linphone_core_get_chat_room(pauline->lc, linphone_chat_room_get_local_address(marieCr));
linphone_core_set_network_reachable(pauline->lc, FALSE);
wait_for_list(coresList, &dummy, 1, 3000);
linphone_core_set_network_reachable(pauline->lc, TRUE);
wait_for_list(coresList, &dummy, 1, 5000);
msg = linphone_chat_room_create_message_from_utf8(marieCr, "And now, did you migrate?");
linphone_chat_message_send(msg);
linphone_chat_message_unref(msg);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneConferenceStateCreationPending,
initialMarieStats.number_of_LinphoneConferenceStateCreationPending + 2, 10000));
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneConferenceStateCreated,
initialMarieStats.number_of_LinphoneConferenceStateCreated + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneChatRoomConferenceJoined,
initialMarieStats.number_of_LinphoneChatRoomConferenceJoined + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(linphone_chat_room_get_capabilities(marieCr) & LinphoneChatRoomCapabilitiesConference);
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(marieCr), 1, int, "%d");
BC_ASSERT_EQUAL(linphone_chat_room_get_history_size(marieCr), 5, int, "%d");
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneConferenceStateCreationPending,
initialPaulineStats.number_of_LinphoneConferenceStateCreationPending + 1, 10000));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneConferenceStateCreated,
initialPaulineStats.number_of_LinphoneConferenceStateCreated + 1, 10000));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneChatRoomConferenceJoined,
initialPaulineStats.number_of_LinphoneChatRoomConferenceJoined + 1,
liblinphone_tester_sip_timeout));
if (paulineCr) {
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageReceived, 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(linphone_chat_room_get_capabilities(paulineCr) & LinphoneChatRoomCapabilitiesConference);
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(paulineCr), 1, int, "%d");
BC_ASSERT_EQUAL(linphone_chat_room_get_history_size(paulineCr), 5, int, "%d");
}
}
// Clean db from chat room
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
}
static void group_chat_donot_room_migrate_from_basic_chat_room(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
bctbx_list_t *coresManagerList = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
4271427242734274427542764277427842794280428142824283428442854286428742884289429042914292429342944295429642974298429943004301430243034304430543064307430843094310431143124313431443154316431743184319432043214322432343244325432643274328432943304331433243334334433543364337433843394340
coresManagerList = bctbx_list_append(coresManagerList, pauline);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
// Create a basic chat room
LinphoneAddress *paulineAddr = linphone_address_new(linphone_core_get_identity(pauline->lc));
LinphoneChatRoom *marieCr = linphone_core_get_chat_room(marie->lc, paulineAddr);
// Send a message and check that a basic chat room is created on Pauline's side
LinphoneChatMessage *msg = linphone_chat_room_create_message_from_utf8(marieCr, "Hey Pauline!");
linphone_chat_message_send(msg);
linphone_chat_message_unref(msg);
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageReceived,
initialPaulineStats.number_of_LinphoneMessageReceived + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_PTR_NOT_NULL(pauline->stat.last_received_chat_message);
if (pauline->stat.last_received_chat_message)
BC_ASSERT_STRING_EQUAL(linphone_chat_message_get_content_type(pauline->stat.last_received_chat_message),
"text/plain");
LinphoneChatRoom *paulineCr =
linphone_core_get_chat_room(pauline->lc, linphone_chat_room_get_local_address(marieCr));
BC_ASSERT_PTR_NOT_NULL(paulineCr);
if (paulineCr) BC_ASSERT_TRUE(linphone_chat_room_get_capabilities(paulineCr) & LinphoneChatRoomCapabilitiesBasic);
// Enable chat room migration and restart core for Marie
coresList = bctbx_list_remove(coresList, marie->lc);
linphone_core_manager_restart(marie, TRUE);
bctbx_list_t *tmpCoresManagerList = bctbx_list_append(NULL, marie);
bctbx_list_t *coresList2 = init_core_for_conference(tmpCoresManagerList);
bctbx_list_free(coresList2);
bctbx_list_free(tmpCoresManagerList);
coresList = bctbx_list_append(coresList, marie->lc);
// Send a new message to initiate chat room migration
marieCr = linphone_core_get_chat_room(marie->lc, paulineAddr);
BC_ASSERT_PTR_NOT_NULL(marieCr);
if (marieCr) {
initialMarieStats = marie->stat;
initialPaulineStats = pauline->stat;
BC_ASSERT_EQUAL(linphone_chat_room_get_capabilities(marieCr),
LinphoneChatRoomCapabilitiesBasic | LinphoneChatRoomCapabilitiesOneToOne, int, "%d");
msg = linphone_chat_room_create_message_from_utf8(marieCr, "Did you migrate?");
linphone_chat_message_send(msg);
linphone_chat_message_unref(msg);
BC_ASSERT_FALSE(wait_for_list(coresList, &marie->stat.number_of_LinphoneConferenceStateCreationPending,
initialMarieStats.number_of_LinphoneConferenceStateCreationPending + 1, 10000));
BC_ASSERT_FALSE(wait_for_list(coresList, &marie->stat.number_of_LinphoneConferenceStateCreated,
initialMarieStats.number_of_LinphoneConferenceStateCreated + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(linphone_chat_room_get_capabilities(marieCr) & LinphoneChatRoomCapabilitiesBasic);
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(marieCr), 1, int, "%d");
BC_ASSERT_EQUAL(linphone_chat_room_get_history_size(marieCr), 2, int, "%d");
BC_ASSERT_FALSE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneConferenceStateCreationPending,
initialPaulineStats.number_of_LinphoneConferenceStateCreationPending + 1, 10000));
BC_ASSERT_FALSE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneConferenceStateCreated,
initialPaulineStats.number_of_LinphoneConferenceStateCreated + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(linphone_chat_room_get_capabilities(paulineCr) & LinphoneChatRoomCapabilitiesBasic);
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(paulineCr), 1, int, "%d");
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageReceived,
initialPaulineStats.number_of_LinphoneMessageReceived + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_EQUAL(linphone_chat_room_get_history_size(paulineCr), 2, int, "%d");
msg = linphone_chat_room_create_message_from_utf8(marieCr, "Let's go drink a beer");
linphone_chat_message_send(msg);
linphone_chat_message_unref(msg);
4341434243434344434543464347434843494350435143524353435443554356435743584359436043614362436343644365436643674368436943704371437243734374437543764377437843794380438143824383438443854386438743884389439043914392439343944395439643974398439944004401440244034404440544064407440844094410
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageReceived,
initialPaulineStats.number_of_LinphoneMessageReceived + 2,
liblinphone_tester_sip_timeout));
BC_ASSERT_EQUAL(linphone_chat_room_get_history_size(marieCr), 3, int, "%d");
BC_ASSERT_EQUAL(linphone_chat_room_get_history_size(paulineCr), 3, int, "%d");
msg = linphone_chat_room_create_message_from_utf8(paulineCr, "Let's go drink mineral water instead");
linphone_chat_message_send(msg);
linphone_chat_message_unref(msg);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneMessageReceived,
initialMarieStats.number_of_LinphoneMessageReceived + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_EQUAL(linphone_chat_room_get_history_size(marieCr), 4, int, "%d");
BC_ASSERT_EQUAL(linphone_chat_room_get_history_size(paulineCr), 4, int, "%d");
}
// Clean db from chat room
linphone_core_delete_chat_room(marie->lc, marieCr);
linphone_core_delete_chat_room(pauline->lc, paulineCr);
linphone_address_unref(paulineAddr);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
}
static void group_chat_room_send_file_with_or_without_text(bool_t with_text, bool_t two_files, bool_t use_buffer) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *chloe = linphone_core_manager_create("chloe_rc");
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
char *sendFilepath = bc_tester_res("sounds/sintel_trailer_opus_h264.mkv");
char *sendFilepath2 = NULL;
char *receivePaulineFilepath = bc_tester_file("receive_file_pauline.dump");
char *receiveChloeFilepath = bc_tester_file("receive_file_chloe.dump");
const char *text = "Hello Group !";
if (two_files) {
sendFilepath2 = bc_tester_res("sounds/ahbahouaismaisbon.wav");
}
/* Globally configure an http file transfer server. */
linphone_core_set_file_transfer_server(marie->lc, file_transfer_url);
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
coresManagerList = bctbx_list_append(coresManagerList, chloe);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(chloe->lc)));
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
stats initialChloeStats = chloe->stat;
/* Remove any previously downloaded file */
remove(receivePaulineFilepath);
remove(receiveChloeFilepath);
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
LinphoneChatRoom *marieCr =
create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject, FALSE,
LinphoneChatRoomEphemeralModeDeviceManaged);
const LinphoneAddress *confAddr = linphone_chat_room_get_conference_address(marieCr);
// Check that the chat room is correctly created on Pauline's side and that the participants are added
4411441244134414441544164417441844194420442144224423442444254426442744284429443044314432443344344435443644374438443944404441444244434444444544464447444844494450445144524453445444554456445744584459446044614462446344644465446644674468446944704471447244734474447544764477447844794480
LinphoneChatRoom *paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats,
confAddr, initialSubject, 2, FALSE);
// Check that the chat room is correctly created on Chloe's side and that the participants are added
LinphoneChatRoom *chloeCr =
check_creation_chat_room_client_side(coresList, chloe, &initialChloeStats, confAddr, initialSubject, 2, FALSE);
// Sending file
if (with_text) {
_send_file_plus_text(marieCr, sendFilepath, sendFilepath2, text, use_buffer);
} else {
_send_file(marieCr, sendFilepath, sendFilepath2, use_buffer);
}
// Check that chat rooms have received the file
if (with_text) {
_receive_file_plus_text(coresList, pauline, &initialPaulineStats, receivePaulineFilepath, sendFilepath,
sendFilepath2, text, use_buffer);
_receive_file_plus_text(coresList, chloe, &initialChloeStats, receiveChloeFilepath, sendFilepath, sendFilepath2,
text, use_buffer);
} else {
_receive_file(coresList, pauline, &initialPaulineStats, receivePaulineFilepath, sendFilepath, sendFilepath2,
use_buffer);
_receive_file(coresList, chloe, &initialChloeStats, receiveChloeFilepath, sendFilepath, sendFilepath2,
use_buffer);
}
// Clean db from chat room
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
linphone_core_manager_delete_chat_room(chloe, chloeCr, coresList);
linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
remove(receivePaulineFilepath);
remove(receiveChloeFilepath);
bc_free(sendFilepath);
if (sendFilepath2) bc_free(sendFilepath2);
bc_free(receivePaulineFilepath);
bc_free(receiveChloeFilepath);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
linphone_core_manager_destroy(chloe);
}
static void group_chat_room_send_file(void) {
group_chat_room_send_file_with_or_without_text(FALSE, FALSE, FALSE);
}
static void group_chat_room_send_file_2(void) {
group_chat_room_send_file_with_or_without_text(FALSE, FALSE, TRUE);
}
static void group_chat_room_send_file_plus_text(void) {
group_chat_room_send_file_with_or_without_text(TRUE, FALSE, FALSE);
}
static void group_chat_room_send_two_files_plus_text(void) {
group_chat_room_send_file_with_or_without_text(TRUE, TRUE, FALSE);
}
static void group_chat_room_send_multipart_custom_content_types(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
4481448244834484448544864487448844894490449144924493449444954496449744984499450045014502450345044505450645074508450945104511451245134514451545164517451845194520452145224523452445254526452745284529453045314532453345344535453645374538453945404541454245434544454545464547454845494550
bctbx_list_t *coresList = init_core_for_conference_with_groupchat_version(coresManagerList, "1.0");
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
const char *initialSubject = "Colleagues";
LinphoneChatRoom *marieCr =
create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject, FALSE,
LinphoneChatRoomEphemeralModeDeviceManaged);
const LinphoneAddress *confAddr = linphone_chat_room_get_conference_address(marieCr);
// Check that the chat room is correctly created on Pauline's side and that the participants are added
LinphoneChatRoom *paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats,
confAddr, initialSubject, 1, FALSE);
// Add our custom content types
linphone_core_add_content_type_support(marie->lc, "application/vnd.3gpp.mcptt-info+xml");
linphone_core_add_content_type_support(marie->lc, "application/vnd.3gpp.mcptt-location-info+xml");
linphone_core_add_content_type_support(pauline->lc, "application/vnd.3gpp.mcptt-info+xml");
linphone_core_add_content_type_support(pauline->lc, "application/vnd.3gpp.mcptt-location-info+xml");
const char *data1 =
"<?xml version=\"1.0\" encoding=\"UTF-8\"?><mcpttinfo xmlns=\"urn:3gpp:ns:mcpttInfo:1.0\" "
"xmlns:xsi=\"http://www.w3.org/2001/XMLSchema-instance\"><mcptt-Params><mcptt-request-uri "
"type=\"Normal\"><mcpttURI>sip:test@sip.example.org</mcpttURI></mcptt-request-uri></mcptt-Params></mcpttinfo>";
const char *data2 =
"<?xml version=\"1.0\" encoding=\"UTF-8\"?><location-info "
"xmlns=\"urn:3gpp:ns:mcpttILocationInfo:1.0\"><Configuration><NonEmergencyLocationInformation><ServingEcgi/"
"><NeighbouringEcgi/><MbmsSaId/><MbsfnArea/><GeographicalCoordinate/><minimumIntervalLength>10</"
"minimumIntervalLength></NonEmergencyLocationInformation><TriggeringCriteria><CellChange><AnyCellChange "
"TriggerId=\"AnyCellChange\"/></CellChange><TrackingAreaChange><AnyTrackingAreaChange "
"TriggerId=\"AnyTrackingAreaChange\"/></TrackingAreaChange><PlmnChange><AnyPlmnChange "
"TriggerId=\"AnyPlmnChange\"/></PlmnChange><PeriodicReport "
"TriggerId=\"Periodic\">20</PeriodicReport><GeographicalAreaChange><AnyAreaChange "
"TriggerId=\"177db491c22\"></AnyAreaChange></GeographicalAreaChange></TriggeringCriteria></Configuration></"
"location-info>";
LinphoneChatMessage *msg;
msg = linphone_chat_room_create_empty_message(marieCr);
LinphoneContent *content = linphone_factory_create_content(linphone_factory_get());
linphone_content_set_type(content, "application");
linphone_content_set_subtype(content, "vnd.3gpp.mcptt-info+xml");
linphone_content_set_utf8_text(content, data1);
linphone_chat_message_add_content(msg, content);
linphone_content_unref(content);
content = linphone_factory_create_content(linphone_factory_get());
linphone_content_set_type(content, "application");
linphone_content_set_subtype(content, "vnd.3gpp.mcptt-location-info+xml");
linphone_content_set_utf8_text(content, data2);
linphone_chat_message_add_content(msg, content);
linphone_content_unref(content);
linphone_chat_message_send(msg);
BC_ASSERT_TRUE(wait_for(pauline->lc, marie->lc, &pauline->stat.number_of_LinphoneMessageReceived, 1));
linphone_chat_message_unref(msg);
if (pauline->stat.last_received_chat_message) {
const bctbx_list_t *contents = linphone_chat_message_get_contents(pauline->stat.last_received_chat_message);
BC_ASSERT_EQUAL((int)bctbx_list_size(contents), 2, int, "%d");
LinphoneContent *content1 = bctbx_list_get_data(contents);
BC_ASSERT_STRING_EQUAL(linphone_content_get_type(content1), "application");
BC_ASSERT_STRING_EQUAL(linphone_content_get_subtype(content1), "vnd.3gpp.mcptt-info+xml");
BC_ASSERT_STRING_EQUAL(linphone_content_get_utf8_text(content1), data1);
LinphoneContent *content2 = bctbx_list_nth_data(contents, 1);
BC_ASSERT_STRING_EQUAL(linphone_content_get_type(content2), "application");
BC_ASSERT_STRING_EQUAL(linphone_content_get_subtype(content2), "vnd.3gpp.mcptt-location-info+xml");
4551455245534554455545564557455845594560456145624563456445654566456745684569457045714572457345744575457645774578457945804581458245834584458545864587458845894590459145924593459445954596459745984599460046014602460346044605460646074608460946104611461246134614461546164617461846194620
BC_ASSERT_STRING_EQUAL(linphone_content_get_utf8_text(content2), data2);
}
// Clean db from chat room
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
}
static void group_chat_room_unique_one_to_one_chat_room_base(bool_t secondDeviceForSender) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *marie2 = NULL;
if (secondDeviceForSender) marie2 = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
if (secondDeviceForSender) coresManagerList = bctbx_list_append(coresManagerList, marie2);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
/* This test was constructed according to 1.0 specification of groupchat.*/
bctbx_list_t *coresList = init_core_for_conference_with_groupchat_version(coresManagerList, "1.0");
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
stats initialMarieStats = marie->stat;
stats initialMarie2Stats;
memset(&initialMarie2Stats, 0, sizeof(initialMarie2Stats));
if (secondDeviceForSender) initialMarie2Stats = marie2->stat;
stats initialPaulineStats = pauline->stat;
// Marie creates a new group chat room
const char *initialSubject = "Pauline";
LinphoneChatRoom *marieCr =
create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject, FALSE,
LinphoneChatRoomEphemeralModeDeviceManaged);
BC_ASSERT_TRUE(linphone_chat_room_get_capabilities(marieCr) & LinphoneChatRoomCapabilitiesOneToOne);
const LinphoneAddress *tmpConfAddr = linphone_chat_room_get_conference_address(marieCr);
if (!tmpConfAddr) {
goto end;
}
LinphoneAddress *confAddr = linphone_address_clone(tmpConfAddr);
// Check that the chat room is correctly created on Pauline's side and that the participants are added
LinphoneChatRoom *paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats,
confAddr, initialSubject, 1, FALSE);
BC_ASSERT_TRUE(linphone_chat_room_get_capabilities(paulineCr) & LinphoneChatRoomCapabilitiesOneToOne);
// Check that the chat room is correctly created on Pauline's side and that the participants are added
LinphoneChatRoom *marie2Cr = NULL;
if (secondDeviceForSender)
marie2Cr = check_creation_chat_room_client_side(coresList, marie2, &initialMarie2Stats, confAddr,
initialSubject, 1, FALSE);
// Marie sends a message
const char *textMessage = "Hello";
LinphoneChatMessage *message = _send_message(marieCr, textMessage);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneMessageDelivered,
initialMarieStats.number_of_LinphoneMessageDelivered + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageReceived,
initialPaulineStats.number_of_LinphoneMessageReceived + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_STRING_EQUAL(linphone_chat_message_get_text(pauline->stat.last_received_chat_message), textMessage);
linphone_chat_message_unref(message);
if (secondDeviceForSender) linphone_core_set_network_reachable(marie2->lc, FALSE);
4621462246234624462546264627462846294630463146324633463446354636463746384639464046414642464346444645464646474648464946504651465246534654465546564657465846594660466146624663466446654666466746684669467046714672467346744675467646774678467946804681468246834684468546864687468846894690
// Marie deletes the chat room
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
wait_for_list(coresList, 0, 1, 2000);
BC_ASSERT_EQUAL(pauline->stat.number_of_participants_removed, initialPaulineStats.number_of_participants_removed,
int, "%d");
// Marie creates the chat room again
initialMarieStats = marie->stat;
initialPaulineStats = pauline->stat;
participantsAddresses = bctbx_list_append(NULL, linphone_address_new(linphone_core_get_identity(pauline->lc)));
marieCr = create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject,
FALSE, LinphoneChatRoomEphemeralModeDeviceManaged);
// Marie sends a new message
textMessage = "Hey again";
message = _send_message(marieCr, textMessage);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneMessageDelivered,
initialMarieStats.number_of_LinphoneMessageDelivered + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageReceived,
initialPaulineStats.number_of_LinphoneMessageReceived + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_STRING_EQUAL(linphone_chat_message_get_text(pauline->stat.last_received_chat_message), textMessage);
linphone_chat_message_unref(message);
// Check that the created address is the same as before
const LinphoneAddress *newConfAddr = linphone_chat_room_get_conference_address(marieCr);
BC_ASSERT_TRUE(linphone_address_weak_equal(confAddr, newConfAddr));
// Clean db from chat room
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
if (secondDeviceForSender) {
linphone_core_set_network_reachable(marie2->lc, TRUE);
linphone_core_delete_chat_room(marie2->lc, marie2Cr);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie2->stat.number_of_LinphoneConferenceStateTerminated,
initialMarie2Stats.number_of_LinphoneConferenceStateTerminated + 1,
liblinphone_tester_sip_timeout));
}
linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
linphone_address_unref(confAddr);
end:
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
if (secondDeviceForSender) linphone_core_manager_destroy(marie2);
linphone_core_manager_destroy(pauline);
}
static void group_chat_room_unique_one_to_one_chat_room(void) {
group_chat_room_unique_one_to_one_chat_room_base(FALSE);
}
static void group_chat_room_unique_one_to_one_chat_room_dual_sender_device(void) {
group_chat_room_unique_one_to_one_chat_room_base(TRUE);
}
static void group_chat_room_unique_one_to_one_chat_room_with_forward_message_recreated_from_message_base(
bool_t with_app_restart, bool_t forward_message, bool_t reply_message) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
/* This test checks the behavior of 1.0 groupchat protocol version, where one-to-one chatroom were supposed to be
* unique. */
bctbx_list_t *coresList = init_core_for_conference_with_groupchat_version(coresManagerList, "1.0");
start_core_for_conference(coresManagerList);
4691469246934694469546964697469846994700470147024703470447054706470747084709471047114712471347144715471647174718471947204721472247234724472547264727472847294730473147324733473447354736473747384739474047414742474347444745474647474748474947504751475247534754475547564757475847594760
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
char *messageId, *secondMessageId = NULL;
// Marie creates a new group chat room
const char *initialSubject = "Pauline";
LinphoneChatRoom *marieCr =
create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject, FALSE,
LinphoneChatRoomEphemeralModeDeviceManaged);
BC_ASSERT_TRUE(linphone_chat_room_get_capabilities(marieCr) & LinphoneChatRoomCapabilitiesOneToOne);
LinphoneAddress *confAddr = linphone_address_clone(linphone_chat_room_get_conference_address(marieCr));
// Check that the chat room is correctly created on Pauline's side and that the participants are added
LinphoneChatRoom *paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats,
confAddr, initialSubject, 1, FALSE);
BC_ASSERT_TRUE(linphone_chat_room_get_capabilities(paulineCr) & LinphoneChatRoomCapabilitiesOneToOne);
// Marie sends a message
const char *textMessage = "Hello";
LinphoneChatMessage *message = _send_message(marieCr, textMessage);
const bctbx_list_t *contents = linphone_chat_message_get_contents(message);
BC_ASSERT_EQUAL((int)bctbx_list_size(contents), 1, int, "%d");
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneMessageDelivered,
initialMarieStats.number_of_LinphoneMessageDelivered + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageReceived,
initialPaulineStats.number_of_LinphoneMessageReceived + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_STRING_EQUAL(linphone_chat_message_get_text(pauline->stat.last_received_chat_message), textMessage);
messageId = bctbx_strdup(linphone_chat_message_get_message_id(message));
linphone_chat_message_unref(message);
if (forward_message) {
BC_ASSERT_EQUAL(linphone_chat_room_get_history_size(paulineCr), 1, int, " %i");
if (linphone_chat_room_get_history_size(paulineCr) > 0) {
bctbx_list_t *history = linphone_chat_room_get_history(paulineCr, 1);
LinphoneChatMessage *recv_msg = (LinphoneChatMessage *)(history->data);
LinphoneChatMessage *msg = linphone_chat_room_create_forward_message(paulineCr, recv_msg);
const LinphoneAddress *forwarded_from_address = linphone_chat_message_get_from_address(recv_msg);
char *forwarded_from = linphone_address_as_string_uri_only(forwarded_from_address);
bctbx_list_free_with_data(history, (bctbx_list_free_func)linphone_chat_message_unref);
LinphoneChatMessageCbs *cbs = linphone_chat_message_get_callbacks(msg);
linphone_chat_message_cbs_set_msg_state_changed(cbs, liblinphone_tester_chat_message_msg_state_changed);
linphone_chat_message_send(msg);
BC_ASSERT_TRUE(linphone_chat_message_is_forward(msg));
BC_ASSERT_STRING_EQUAL(linphone_chat_message_get_forward_info(msg), forwarded_from);
BC_ASSERT_TRUE(wait_for(pauline->lc, marie->lc, &pauline->stat.number_of_LinphoneMessageDelivered, 1));
BC_ASSERT_TRUE(wait_for(pauline->lc, marie->lc, &marie->stat.number_of_LinphoneMessageReceived, 1));
BC_ASSERT_PTR_NOT_NULL(marie->stat.last_received_chat_message);
if (marie->stat.last_received_chat_message != NULL) {
BC_ASSERT_EQUAL(linphone_chat_room_get_history_size(marieCr), 2, int, " %i");
BC_ASSERT_STRING_EQUAL(linphone_chat_message_get_text(marie->stat.last_received_chat_message),
textMessage);
BC_ASSERT_STRING_EQUAL(linphone_chat_message_get_text_content(marie->stat.last_received_chat_message),
textMessage);
BC_ASSERT_TRUE(linphone_chat_message_is_forward(marie->stat.last_received_chat_message));
BC_ASSERT_STRING_EQUAL(linphone_chat_message_get_forward_info(marie->stat.last_received_chat_message),
forwarded_from);
}
linphone_chat_message_unref(msg);
4761476247634764476547664767476847694770477147724773477447754776477747784779478047814782478347844785478647874788478947904791479247934794479547964797479847994800480148024803480448054806480748084809481048114812481348144815481648174818481948204821482248234824482548264827482848294830
ms_free(forwarded_from);
}
} else if (reply_message) {
BC_ASSERT_EQUAL(linphone_chat_room_get_history_size(paulineCr), 1, int, " %i");
if (linphone_chat_room_get_history_size(paulineCr) > 0) {
bctbx_list_t *history = linphone_chat_room_get_history(paulineCr, 1);
LinphoneChatMessage *recv_msg = (LinphoneChatMessage *)(history->data);
LinphoneChatMessage *msg = linphone_chat_room_create_reply_message(paulineCr, recv_msg);
BC_ASSERT_TRUE(linphone_chat_message_is_reply(msg));
const char *replyId = linphone_chat_message_get_reply_message_id(msg);
BC_ASSERT_STRING_EQUAL(replyId, messageId);
linphone_chat_message_add_utf8_text_content(msg, "Quite funny!");
BC_ASSERT_TRUE(linphone_address_weak_equal(linphone_chat_message_get_reply_message_sender_address(msg),
linphone_chat_message_get_from_address(recv_msg)));
LinphoneChatMessage *orig = linphone_chat_message_get_reply_message(msg);
BC_ASSERT_PTR_NOT_NULL(orig);
BC_ASSERT_PTR_EQUAL(orig, recv_msg);
if (orig) {
const char *reply = linphone_chat_message_get_utf8_text(orig);
BC_ASSERT_STRING_EQUAL(reply, "Hello");
linphone_chat_message_unref(orig);
}
bctbx_list_free_with_data(history, (bctbx_list_free_func)linphone_chat_message_unref);
LinphoneChatMessageCbs *cbs = linphone_chat_message_get_callbacks(msg);
linphone_chat_message_cbs_set_msg_state_changed(cbs, liblinphone_tester_chat_message_msg_state_changed);
linphone_chat_message_send(msg);
BC_ASSERT_TRUE(wait_for(pauline->lc, marie->lc, &pauline->stat.number_of_LinphoneMessageDelivered, 1));
BC_ASSERT_TRUE(wait_for(pauline->lc, marie->lc, &marie->stat.number_of_LinphoneMessageReceived, 1));
BC_ASSERT_PTR_NOT_NULL(marie->stat.last_received_chat_message);
if (marie->stat.last_received_chat_message != NULL) {
BC_ASSERT_EQUAL(linphone_chat_room_get_history_size(marieCr), 2, int, " %i");
BC_ASSERT_STRING_EQUAL(linphone_chat_message_get_text(marie->stat.last_received_chat_message),
"Quite funny!");
BC_ASSERT_STRING_EQUAL(linphone_chat_message_get_text_content(marie->stat.last_received_chat_message),
"Quite funny!");
BC_ASSERT_TRUE(linphone_chat_message_is_reply(marie->stat.last_received_chat_message));
BC_ASSERT_STRING_EQUAL(
linphone_chat_message_get_reply_message_id(marie->stat.last_received_chat_message), messageId);
BC_ASSERT_TRUE(linphone_address_weak_equal(linphone_chat_message_get_reply_message_sender_address(msg),
linphone_chat_room_get_local_address(marieCr)));
}
secondMessageId = bctbx_strdup(linphone_chat_message_get_message_id(msg));
linphone_chat_message_unref(msg);
}
}
if (with_app_restart) {
// To simulate dialog removal
LinphoneAddress *marieAddr = linphone_address_clone(linphone_chat_room_get_peer_address(marieCr));
linphone_core_set_network_reachable(marie->lc, FALSE);
coresList = bctbx_list_remove(coresList, marie->lc);
linphone_core_manager_reinit(marie);
bctbx_list_t *tmpCoresManagerList = bctbx_list_append(NULL, marie);
bctbx_list_t *tmpCoresList = init_core_for_conference(tmpCoresManagerList);
bctbx_list_free(tmpCoresManagerList);
coresList = bctbx_list_concat(coresList, tmpCoresList);
linphone_core_manager_start(marie, TRUE);
marieCr = linphone_core_get_chat_room(marie->lc, marieAddr);
linphone_address_unref(marieAddr);
}
4831483248334834483548364837483848394840484148424843484448454846484748484849485048514852485348544855485648574858485948604861486248634864486548664867486848694870487148724873487448754876487748784879488048814882488348844885488648874888488948904891489248934894489548964897489848994900
if (forward_message) {
BC_ASSERT_EQUAL(linphone_chat_room_get_history_size(marieCr), 2, int, " %i");
if (linphone_chat_room_get_history_size(marieCr) > 1) {
LinphoneChatMessage *recv_msg = linphone_chat_room_get_last_message_in_history(marieCr);
BC_ASSERT_TRUE(linphone_chat_message_is_forward(recv_msg));
// for marie, forward message by anonymous
LinphoneChatMessage *msgFromMarie = linphone_chat_room_create_forward_message(marieCr, recv_msg);
linphone_chat_message_send(msgFromMarie);
BC_ASSERT_TRUE(linphone_chat_message_is_forward(msgFromMarie));
BC_ASSERT_STRING_EQUAL(linphone_chat_message_get_forward_info(msgFromMarie), "Anonymous");
linphone_chat_message_unref(msgFromMarie);
linphone_chat_message_unref(recv_msg);
}
} else if (reply_message) {
BC_ASSERT_EQUAL(linphone_chat_room_get_history_size(marieCr), 2, int, " %i");
if (linphone_chat_room_get_history_size(marieCr) > 1) {
LinphoneChatMessage *recv_msg = linphone_chat_room_get_last_message_in_history(marieCr);
const char *body = linphone_chat_message_get_utf8_text(recv_msg);
BC_ASSERT_STRING_EQUAL(body, "Quite funny!");
BC_ASSERT_TRUE(linphone_chat_message_is_reply(recv_msg));
BC_ASSERT_STRING_EQUAL(linphone_chat_message_get_reply_message_id(recv_msg), messageId);
BC_ASSERT_STRING_EQUAL(linphone_chat_message_get_message_id(recv_msg), secondMessageId);
LinphoneChatMessage *orig = linphone_chat_message_get_reply_message(recv_msg);
BC_ASSERT_PTR_NOT_NULL(orig);
if (orig) {
const char *reply = linphone_chat_message_get_utf8_text(orig);
BC_ASSERT_STRING_EQUAL(reply, "Hello");
linphone_chat_message_unref(orig);
}
LinphoneChatMessage *msgFromMarie = linphone_chat_room_create_reply_message(marieCr, recv_msg);
BC_ASSERT_TRUE(linphone_address_weak_equal(linphone_chat_message_get_reply_message_sender_address(recv_msg),
linphone_chat_message_get_from_address(msgFromMarie)));
BC_ASSERT_TRUE(linphone_chat_message_is_reply(msgFromMarie));
linphone_chat_message_add_utf8_text_content(msgFromMarie, "Still laughing!");
linphone_chat_message_send(msgFromMarie);
linphone_chat_message_unref(msgFromMarie);
linphone_chat_message_unref(recv_msg);
}
} else {
// Marie deletes the chat room
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
wait_for_list(coresList, 0, 1, 2000);
BC_ASSERT_EQUAL(pauline->stat.number_of_participants_removed,
initialPaulineStats.number_of_participants_removed, int, "%d");
// Pauline sends a new message
initialMarieStats = marie->stat;
initialPaulineStats = pauline->stat;
// Pauline sends a new message
textMessage = "Hey you";
message = _send_message(paulineCr, textMessage);
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageDelivered,
initialPaulineStats.number_of_LinphoneMessageDelivered + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneMessageReceived,
initialMarieStats.number_of_LinphoneMessageReceived + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_STRING_EQUAL(linphone_chat_message_get_text(marie->stat.last_received_chat_message), textMessage);
linphone_chat_message_unref(message);
4901490249034904490549064907490849094910491149124913491449154916491749184919492049214922492349244925492649274928492949304931493249334934493549364937493849394940494149424943494449454946494749484949495049514952495349544955495649574958495949604961496249634964496549664967496849694970
// Check that the chat room has been correctly recreated on Marie's side
marieCr = check_creation_chat_room_client_side(coresList, marie, &initialMarieStats, confAddr, initialSubject,
1, FALSE);
BC_ASSERT_TRUE(linphone_chat_room_get_capabilities(paulineCr) & LinphoneChatRoomCapabilitiesOneToOne);
}
if (messageId) bc_free(messageId);
if (secondMessageId) bc_free(secondMessageId);
// Clean db from chat room
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
wait_for_list(coresList, 0, 1, 2000);
BC_ASSERT_EQUAL(linphone_core_get_call_history_size(marie->lc), 0, int, "%i");
BC_ASSERT_EQUAL(linphone_core_get_call_history_size(pauline->lc), 0, int, "%i");
BC_ASSERT_PTR_NULL(linphone_core_get_call_logs(marie->lc));
BC_ASSERT_PTR_NULL(linphone_core_get_call_logs(pauline->lc));
linphone_address_unref(confAddr);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
}
static void group_chat_room_unique_one_to_one_chat_room_recreated_from_message_base(bool_t with_app_restart) {
group_chat_room_unique_one_to_one_chat_room_with_forward_message_recreated_from_message_base(with_app_restart,
FALSE, FALSE);
}
static void group_chat_room_unique_one_to_one_chat_room_recreated_from_message(void) {
group_chat_room_unique_one_to_one_chat_room_recreated_from_message_base(FALSE);
}
static void group_chat_room_unique_one_to_one_chat_room_recreated_from_message_with_app_restart(void) {
group_chat_room_unique_one_to_one_chat_room_recreated_from_message_base(TRUE);
}
static void group_chat_room_unique_one_to_one_chat_room_recreated_from_message_2(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
// Create a second device for Marie, but it is inactive after registration in this test
LinphoneCoreManager *marie2 = linphone_core_manager_create("marie_rc");
// Create a second device for Pauline, but again inactivate it after registration
LinphoneCoreManager *pauline2 = linphone_core_manager_create("pauline_rc");
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
coresManagerList = bctbx_list_append(coresManagerList, marie2);
coresManagerList = bctbx_list_append(coresManagerList, pauline2);
bctbx_list_t *coresList = init_core_for_conference_with_groupchat_version(coresManagerList, "1.0");
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
stats initialMarie2Stats = marie2->stat;
stats initialPauline2Stats = pauline2->stat;
linphone_core_set_network_reachable(marie2->lc, FALSE);
linphone_core_set_network_reachable(pauline2->lc, FALSE);
// Marie creates a new group chat room
const char *initialSubject = "Pauline";
LinphoneChatRoom *marieCr =
create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject, FALSE,
LinphoneChatRoomEphemeralModeDeviceManaged);
4971497249734974497549764977497849794980498149824983498449854986498749884989499049914992499349944995499649974998499950005001500250035004500550065007500850095010501150125013501450155016501750185019502050215022502350245025502650275028502950305031503250335034503550365037503850395040
BC_ASSERT_TRUE(linphone_chat_room_get_capabilities(marieCr) & LinphoneChatRoomCapabilitiesOneToOne);
LinphoneAddress *confAddr = linphone_address_clone(linphone_chat_room_get_conference_address(marieCr));
// Check that the chat room is correctly created on Pauline's side and that the participants are added
LinphoneChatRoom *paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats,
confAddr, initialSubject, 1, FALSE);
BC_ASSERT_TRUE(linphone_chat_room_get_capabilities(paulineCr) & LinphoneChatRoomCapabilitiesOneToOne);
// Marie sends a message
const char *textMessage = "Hello";
LinphoneChatMessage *message = _send_message(marieCr, textMessage);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneMessageDelivered,
initialMarieStats.number_of_LinphoneMessageDelivered + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageReceived,
initialPaulineStats.number_of_LinphoneMessageReceived + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_STRING_EQUAL(linphone_chat_message_get_text(pauline->stat.last_received_chat_message), textMessage);
linphone_chat_message_unref(message);
// Marie deletes the chat room
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
wait_for_list(coresList, 0, 1, 2000);
BC_ASSERT_EQUAL(pauline->stat.number_of_participants_removed, initialPaulineStats.number_of_participants_removed,
int, "%d");
// Marie sends a new message
participantsAddresses = NULL;
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
initialMarieStats = marie->stat;
initialPaulineStats = pauline->stat;
marieCr = create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject,
FALSE, LinphoneChatRoomEphemeralModeDeviceManaged);
// Check that the chat room has been correctly recreated on Marie's side
marieCr =
check_creation_chat_room_client_side(coresList, marie, &initialMarieStats, confAddr, initialSubject, 1, FALSE);
if (BC_ASSERT_PTR_NOT_NULL(marieCr)) {
BC_ASSERT_TRUE(linphone_chat_room_get_capabilities(marieCr) & LinphoneChatRoomCapabilitiesOneToOne);
textMessage = "Hey you";
message = _send_message(marieCr, textMessage);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneMessageDelivered,
initialMarieStats.number_of_LinphoneMessageDelivered + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageReceived,
initialPaulineStats.number_of_LinphoneMessageReceived + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_STRING_EQUAL(linphone_chat_message_get_text(pauline->stat.last_received_chat_message), textMessage);
linphone_chat_message_unref(message);
}
// Clean db from chat room
linphone_core_set_network_reachable(marie2->lc, TRUE);
linphone_core_set_network_reachable(pauline2->lc, TRUE);
LinphoneChatRoom *paulineCr2 = check_creation_chat_room_client_side(coresList, pauline2, &initialPauline2Stats,
confAddr, initialSubject, 1, FALSE);
LinphoneChatRoom *marieCr2 = check_creation_chat_room_client_side(coresList, marie2, &initialMarie2Stats, confAddr,
initialSubject, 1, FALSE);
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
linphone_core_manager_delete_chat_room(marie2, marieCr2, coresList);
linphone_core_manager_delete_chat_room(pauline2, paulineCr2, coresList);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneConferenceStateTerminated,
initialMarieStats.number_of_LinphoneConferenceStateTerminated + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneConferenceStateTerminated,
5041504250435044504550465047504850495050505150525053505450555056505750585059506050615062506350645065506650675068506950705071507250735074507550765077507850795080508150825083508450855086508750885089509050915092509350945095509650975098509951005101510251035104510551065107510851095110
initialPaulineStats.number_of_LinphoneConferenceStateTerminated + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &marie2->stat.number_of_LinphoneConferenceStateTerminated,
initialMarie2Stats.number_of_LinphoneConferenceStateTerminated + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline2->stat.number_of_LinphoneConferenceStateTerminated,
initialPauline2Stats.number_of_LinphoneConferenceStateTerminated + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_EQUAL(linphone_core_get_call_history_size(marie->lc), 0, int, "%i");
BC_ASSERT_EQUAL(linphone_core_get_call_history_size(pauline->lc), 0, int, "%i");
BC_ASSERT_PTR_NULL(linphone_core_get_call_logs(marie->lc));
BC_ASSERT_PTR_NULL(linphone_core_get_call_logs(pauline->lc));
linphone_address_unref(confAddr);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
linphone_core_manager_destroy(marie2);
linphone_core_manager_destroy(pauline2);
}
static void group_chat_room_join_one_to_one_chat_room_with_a_new_device(void) {
LinphoneCoreManager *marie1 = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
bctbx_list_t *coresManagerList = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie1);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
bctbx_list_t *participantsAddresses =
bctbx_list_append(NULL, linphone_address_new(linphone_core_get_identity(pauline->lc)));
stats initialMarie1Stats = marie1->stat;
stats initialPaulineStats = pauline->stat;
// Marie1 creates a new one-to-one chat room with Pauline
const char *initialSubject = "Pauline";
LinphoneChatRoom *marie1Cr =
create_chat_room_client_side(coresList, marie1, &initialMarie1Stats, participantsAddresses, initialSubject,
FALSE, LinphoneChatRoomEphemeralModeDeviceManaged);
BC_ASSERT_TRUE(linphone_chat_room_get_capabilities(marie1Cr) & LinphoneChatRoomCapabilitiesOneToOne);
LinphoneAddress *confAddr = linphone_address_clone(linphone_chat_room_get_conference_address(marie1Cr));
// Check that the chat room is correctly created on Pauline's side and that the participants are added
LinphoneChatRoom *paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats,
confAddr, initialSubject, 1, FALSE);
BC_ASSERT_TRUE(linphone_chat_room_get_capabilities(paulineCr) & LinphoneChatRoomCapabilitiesOneToOne);
// Marie1 sends a message
const char *textMessage = "Hello";
LinphoneChatMessage *message = _send_message(marie1Cr, textMessage);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie1->stat.number_of_LinphoneMessageDelivered,
initialMarie1Stats.number_of_LinphoneMessageDelivered + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageReceived,
initialPaulineStats.number_of_LinphoneMessageReceived + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_STRING_EQUAL(linphone_chat_message_get_text(pauline->stat.last_received_chat_message), textMessage);
linphone_chat_message_unref(message);
// Pauline answers to the previous message
textMessage = "Hey. How are you?";
message = _send_message(paulineCr, textMessage);
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageDelivered,
initialPaulineStats.number_of_LinphoneMessageDelivered + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &marie1->stat.number_of_LinphoneMessageReceived,
initialMarie1Stats.number_of_LinphoneMessageReceived + 1,
5111511251135114511551165117511851195120512151225123512451255126512751285129513051315132513351345135513651375138513951405141514251435144514551465147514851495150515151525153515451555156515751585159516051615162516351645165516651675168516951705171517251735174517551765177517851795180
liblinphone_tester_sip_timeout));
BC_ASSERT_STRING_EQUAL(linphone_chat_message_get_text(marie1->stat.last_received_chat_message), textMessage);
linphone_chat_message_unref(message);
// Simulate an uninstall of the application on Marie's side
linphone_core_set_network_reachable(marie1->lc, FALSE);
coresManagerList = bctbx_list_remove(coresManagerList, marie1);
coresList = bctbx_list_remove(coresList, marie1->lc);
LinphoneCoreManager *marie2 = linphone_core_manager_create("marie_rc");
stats initialMarie2Stats = marie2->stat;
bctbx_list_t *newCoresManagerList = bctbx_list_append(NULL, marie2);
bctbx_list_t *newCoresList = init_core_for_conference(newCoresManagerList);
start_core_for_conference(newCoresManagerList);
coresManagerList = bctbx_list_concat(coresManagerList, newCoresManagerList);
coresList = bctbx_list_concat(coresList, newCoresList);
// Marie2 gets the one-to-one chat room with Pauline
LinphoneChatRoom *marie2Cr = check_creation_chat_room_client_side(coresList, marie2, &initialMarie2Stats, confAddr,
initialSubject, 1, FALSE);
BC_ASSERT_TRUE(linphone_chat_room_get_capabilities(marie2Cr) & LinphoneChatRoomCapabilitiesOneToOne);
// Marie2 sends a new message
textMessage = "Fine and you?";
message = _send_message(marie2Cr, textMessage);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie2->stat.number_of_LinphoneMessageDelivered,
initialMarie2Stats.number_of_LinphoneMessageDelivered + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageReceived,
initialPaulineStats.number_of_LinphoneMessageReceived + 2,
liblinphone_tester_sip_timeout));
BC_ASSERT_STRING_EQUAL(linphone_chat_message_get_text(pauline->stat.last_received_chat_message), textMessage);
linphone_chat_message_unref(message);
// Pauline answers to the previous message
textMessage = "Perfect!";
message = _send_message(paulineCr, textMessage);
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageDelivered,
initialPaulineStats.number_of_LinphoneMessageDelivered + 2,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &marie2->stat.number_of_LinphoneMessageReceived,
initialMarie2Stats.number_of_LinphoneMessageReceived + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_STRING_EQUAL(linphone_chat_message_get_text(marie2->stat.last_received_chat_message), textMessage);
linphone_chat_message_unref(message);
// Clean db from chat room
int previousNbRegistrationOk = marie1->stat.number_of_LinphoneRegistrationOk;
linphone_core_set_network_reachable(marie1->lc, TRUE);
wait_for_until(marie1->lc, NULL, &marie1->stat.number_of_LinphoneRegistrationOk, previousNbRegistrationOk + 1,
2000);
linphone_core_manager_delete_chat_room(marie2, marie2Cr, coresList);
linphone_core_delete_chat_room(marie1->lc, marie1Cr);
linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
linphone_address_unref(confAddr);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie2);
linphone_core_manager_destroy(marie1);
linphone_core_manager_destroy(pauline);
}
static void group_chat_room_new_unique_one_to_one_chat_room_after_both_participants_left(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
bctbx_list_t *coresList = init_core_for_conference_with_groupchat_version(coresManagerList, "1.0");
5181518251835184518551865187518851895190519151925193519451955196519751985199520052015202520352045205520652075208520952105211521252135214521552165217521852195220522152225223522452255226522752285229523052315232523352345235523652375238523952405241524252435244524552465247524852495250
;
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
// Marie creates a new group chat room
const char *initialSubject = "Pauline";
LinphoneChatRoom *marieCr =
create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject, FALSE,
LinphoneChatRoomEphemeralModeDeviceManaged);
BC_ASSERT_TRUE(linphone_chat_room_get_capabilities(marieCr) & LinphoneChatRoomCapabilitiesOneToOne);
LinphoneAddress *firstConfAddr = linphone_address_clone(linphone_chat_room_get_conference_address(marieCr));
// Check that the chat room is correctly created on Pauline's side and that the participants are added
LinphoneChatRoom *paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats,
firstConfAddr, initialSubject, 1, FALSE);
BC_ASSERT_TRUE(linphone_chat_room_get_capabilities(paulineCr) & LinphoneChatRoomCapabilitiesOneToOne);
// Both participants delete the chat room
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
wait_for_list(coresList, 0, 1, 3000);
// Marie re-creates a chat room with Pauline
initialMarieStats = marie->stat;
initialPaulineStats = pauline->stat;
participantsAddresses = NULL;
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
marieCr = create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject,
FALSE, LinphoneChatRoomEphemeralModeDeviceManaged);
BC_ASSERT_TRUE(linphone_chat_room_get_capabilities(marieCr) & LinphoneChatRoomCapabilitiesOneToOne);
LinphoneAddress *secondConfAddr = linphone_address_clone(linphone_chat_room_get_conference_address(marieCr));
// Check that the chat room has been correctly recreated on Marie's side
paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats, secondConfAddr,
initialSubject, 1, FALSE);
BC_ASSERT_TRUE(linphone_chat_room_get_capabilities(paulineCr) & LinphoneChatRoomCapabilitiesOneToOne);
/* firstconfAddr and secondConfAddr must differ */
BC_ASSERT_FALSE(linphone_address_equal(firstConfAddr, secondConfAddr));
// Clean db from chat room
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
linphone_address_unref(firstConfAddr);
linphone_address_unref(secondConfAddr);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
}
static void imdn_for_group_chat_room(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *chloe = linphone_core_manager_create("chloe_rc");
LinphoneCoreManager *marie2 = linphone_core_manager_create("marie_rc");
LinphoneChatRoom *marieCr = NULL, *marie2Cr = NULL, *paulineCr = NULL, *chloeCr = NULL;
const LinphoneAddress *confAddr = NULL;
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
coresManagerList = bctbx_list_append(coresManagerList, chloe);
5251525252535254525552565257525852595260526152625263526452655266526752685269527052715272527352745275527652775278527952805281528252835284528552865287528852895290529152925293529452955296529752985299530053015302530353045305530653075308530953105311531253135314531553165317531853195320
coresManagerList = bctbx_list_append(coresManagerList, marie2);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(chloe->lc)));
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
stats initialChloeStats = chloe->stat;
stats initialMarie2Stats = marie2->stat;
time_t initialTime = ms_time(NULL);
// Enable IMDN
linphone_im_notif_policy_enable_all(linphone_core_get_im_notif_policy(marie->lc));
linphone_im_notif_policy_enable_all(linphone_core_get_im_notif_policy(pauline->lc));
linphone_im_notif_policy_enable_all(linphone_core_get_im_notif_policy(chloe->lc));
linphone_im_notif_policy_enable_all(linphone_core_get_im_notif_policy(marie2->lc));
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
marieCr = create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject,
FALSE, LinphoneChatRoomEphemeralModeDeviceManaged);
if (!BC_ASSERT_PTR_NOT_NULL(marieCr)) goto end;
confAddr = linphone_chat_room_get_conference_address(marieCr);
if (!BC_ASSERT_PTR_NOT_NULL(confAddr)) goto end;
// Check that the chat room is correctly created on Pauline's side and that the participants are added
paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats, confAddr, initialSubject,
2, FALSE);
if (!BC_ASSERT_PTR_NOT_NULL(paulineCr)) goto end;
// Check that the chat room is correctly created on Chloe's side and that the participants are added
chloeCr =
check_creation_chat_room_client_side(coresList, chloe, &initialChloeStats, confAddr, initialSubject, 2, FALSE);
if (!BC_ASSERT_PTR_NOT_NULL(chloeCr)) goto end;
marie2Cr =
check_creation_chat_room_client_side(coresList, marie2, &initialMarie2Stats, confAddr, initialSubject, 2, TRUE);
if (!BC_ASSERT_PTR_NOT_NULL(marie2Cr)) goto end;
// Chloe begins composing a message
const char *chloeTextMessage = "Hello";
LinphoneChatMessage *chloeMessage = _send_message(chloeCr, chloeTextMessage);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneMessageReceived,
initialMarieStats.number_of_LinphoneMessageReceived + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &marie2->stat.number_of_LinphoneMessageReceived,
initialMarie2Stats.number_of_LinphoneMessageReceived + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageReceived,
initialPaulineStats.number_of_LinphoneMessageReceived + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &chloe->stat.number_of_LinphoneMessageSent, 1, 1000));
LinphoneChatMessage *marieLastMsg = marie->stat.last_received_chat_message;
if (!BC_ASSERT_PTR_NOT_NULL(marieLastMsg)) goto end;
BC_ASSERT_STRING_EQUAL(linphone_chat_message_get_text(marieLastMsg), chloeTextMessage);
LinphoneAddress *chloeAddr = linphone_address_new(linphone_core_get_identity(chloe->lc));
BC_ASSERT_TRUE(linphone_address_weak_equal(chloeAddr, linphone_chat_message_get_from_address(marieLastMsg)));
linphone_address_unref(chloeAddr);
// Check that the message has been delivered to Marie and Pauline
BC_ASSERT_TRUE(wait_for_list(coresList, &chloe->stat.number_of_LinphoneMessageDeliveredToUser,
initialChloeStats.number_of_LinphoneMessageDeliveredToUser + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_PTR_NULL(
linphone_chat_message_get_participants_by_imdn_state(chloeMessage, LinphoneChatMessageStateDisplayed));
bctbx_list_t *participantsThatReceivedChloeMessage =
linphone_chat_message_get_participants_by_imdn_state(chloeMessage, LinphoneChatMessageStateDeliveredToUser);
5321532253235324532553265327532853295330533153325333533453355336533753385339534053415342534353445345534653475348534953505351535253535354535553565357535853595360536153625363536453655366536753685369537053715372537353745375537653775378537953805381538253835384538553865387538853895390
if (BC_ASSERT_PTR_NOT_NULL(participantsThatReceivedChloeMessage)) {
BC_ASSERT_EQUAL((int)bctbx_list_size(participantsThatReceivedChloeMessage), 2, int, "%d");
for (bctbx_list_t *item = participantsThatReceivedChloeMessage; item; item = bctbx_list_next(item)) {
LinphoneParticipantImdnState *state = (LinphoneParticipantImdnState *)bctbx_list_get_data(item);
BC_ASSERT_GREATER((int)linphone_participant_imdn_state_get_state_change_time(state), (int)initialTime, int,
"%d");
BC_ASSERT_EQUAL(linphone_participant_imdn_state_get_state(state), LinphoneChatMessageStateDeliveredToUser,
int, "%d");
BC_ASSERT_PTR_NOT_NULL(linphone_participant_imdn_state_get_participant(state));
}
bctbx_list_free_with_data(participantsThatReceivedChloeMessage,
(bctbx_list_free_func)linphone_participant_imdn_state_unref);
}
BC_ASSERT_PTR_NULL(
linphone_chat_message_get_participants_by_imdn_state(chloeMessage, LinphoneChatMessageStateDelivered));
BC_ASSERT_PTR_NULL(
linphone_chat_message_get_participants_by_imdn_state(chloeMessage, LinphoneChatMessageStateNotDelivered));
// Marie marks the message as read, check that the state is not yet displayed on Chloe's side
linphone_chat_room_mark_as_read(marieCr);
BC_ASSERT_FALSE(wait_for_list(coresList, &chloe->stat.number_of_LinphoneMessageDisplayed,
initialChloeStats.number_of_LinphoneMessageDisplayed + 1, 3000));
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneMessageSent, 0, 1000));
bctbx_list_t *participantsThatDisplayedChloeMessage =
linphone_chat_message_get_participants_by_imdn_state(chloeMessage, LinphoneChatMessageStateDisplayed);
if (BC_ASSERT_PTR_NOT_NULL(participantsThatDisplayedChloeMessage)) {
BC_ASSERT_EQUAL((int)bctbx_list_size(participantsThatDisplayedChloeMessage), 1, int, "%d");
bctbx_list_free_with_data(participantsThatDisplayedChloeMessage,
(bctbx_list_free_func)linphone_participant_imdn_state_unref);
}
participantsThatReceivedChloeMessage =
linphone_chat_message_get_participants_by_imdn_state(chloeMessage, LinphoneChatMessageStateDeliveredToUser);
if (BC_ASSERT_PTR_NOT_NULL(participantsThatReceivedChloeMessage)) {
BC_ASSERT_EQUAL((int)bctbx_list_size(participantsThatReceivedChloeMessage), 1, int, "%d");
bctbx_list_free_with_data(participantsThatReceivedChloeMessage,
(bctbx_list_free_func)linphone_participant_imdn_state_unref);
}
BC_ASSERT_PTR_NULL(
linphone_chat_message_get_participants_by_imdn_state(chloeMessage, LinphoneChatMessageStateDelivered));
BC_ASSERT_PTR_NULL(
linphone_chat_message_get_participants_by_imdn_state(chloeMessage, LinphoneChatMessageStateNotDelivered));
// Marie2 should have received marie's Display IMDN, causing it's own chatroom to be marked as read as well
// automatically
BC_ASSERT_EQUAL(linphone_chat_room_get_unread_messages_count(marie2Cr), 0, int, "%d");
// Pauline also marks the message as read, check that the state is now displayed on Chloe's side
linphone_chat_room_mark_as_read(paulineCr);
BC_ASSERT_TRUE(wait_for_list(coresList, &chloe->stat.number_of_LinphoneMessageDisplayed,
initialChloeStats.number_of_LinphoneMessageDisplayed + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageSent, 0, 1000));
participantsThatDisplayedChloeMessage =
linphone_chat_message_get_participants_by_imdn_state(chloeMessage, LinphoneChatMessageStateDisplayed);
if (BC_ASSERT_PTR_NOT_NULL(participantsThatDisplayedChloeMessage)) {
BC_ASSERT_EQUAL((int)bctbx_list_size(participantsThatDisplayedChloeMessage), 2, int, "%d");
bctbx_list_free_with_data(participantsThatDisplayedChloeMessage,
(bctbx_list_free_func)linphone_participant_imdn_state_unref);
}
BC_ASSERT_PTR_NULL(
linphone_chat_message_get_participants_by_imdn_state(chloeMessage, LinphoneChatMessageStateDeliveredToUser));
BC_ASSERT_PTR_NULL(
linphone_chat_message_get_participants_by_imdn_state(chloeMessage, LinphoneChatMessageStateDelivered));
BC_ASSERT_PTR_NULL(
linphone_chat_message_get_participants_by_imdn_state(chloeMessage, LinphoneChatMessageStateNotDelivered));
linphone_chat_message_unref(chloeMessage);
end:
// Clean db from chat room
5391539253935394539553965397539853995400540154025403540454055406540754085409541054115412541354145415541654175418541954205421542254235424542554265427542854295430543154325433543454355436543754385439544054415442544354445445544654475448544954505451545254535454545554565457545854595460
if (marieCr) linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
if (chloeCr) linphone_core_manager_delete_chat_room(chloe, chloeCr, coresList);
if (paulineCr) linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
if (marie2Cr) linphone_core_manager_delete_chat_room(marie2, marie2Cr, coresList);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(marie2);
linphone_core_manager_destroy(pauline);
linphone_core_manager_destroy(chloe);
}
static void imdn_updated_for_group_chat_room_with_one_participant_offline(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *chloe = linphone_core_manager_create("chloe_rc");
LinphoneChatRoom *marieCr = NULL, *paulineCr = NULL, *chloeCr = NULL;
const LinphoneAddress *confAddr = NULL;
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
coresManagerList = bctbx_list_append(coresManagerList, chloe);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(chloe->lc)));
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
stats initialChloeStats = chloe->stat;
// Enable IMDN
linphone_im_notif_policy_enable_all(linphone_core_get_im_notif_policy(marie->lc));
linphone_im_notif_policy_enable_all(linphone_core_get_im_notif_policy(pauline->lc));
linphone_im_notif_policy_enable_all(linphone_core_get_im_notif_policy(chloe->lc));
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
marieCr = create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject,
FALSE, LinphoneChatRoomEphemeralModeDeviceManaged);
if (!BC_ASSERT_PTR_NOT_NULL(marieCr)) goto end;
confAddr = linphone_chat_room_get_conference_address(marieCr);
if (!BC_ASSERT_PTR_NOT_NULL(confAddr)) goto end;
// Check that the chat room is correctly created on Pauline's side and that the participants are added
paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats, confAddr, initialSubject,
2, FALSE);
if (!BC_ASSERT_PTR_NOT_NULL(paulineCr)) goto end;
// Check that the chat room is correctly created on Chloe's side and that the participants are added
chloeCr =
check_creation_chat_room_client_side(coresList, chloe, &initialChloeStats, confAddr, initialSubject, 2, FALSE);
if (!BC_ASSERT_PTR_NOT_NULL(chloeCr)) goto end;
// pauline offline
linphone_core_set_network_reachable(pauline->lc, FALSE);
// Chloe begins composing a message
const char *chloeTextMessage = "Hello";
LinphoneChatMessage *chloeMessage = _send_message(chloeCr, chloeTextMessage);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneMessageReceived,
initialMarieStats.number_of_LinphoneMessageReceived + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_FALSE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageReceived,
initialPaulineStats.number_of_LinphoneMessageReceived + 1,
liblinphone_tester_sip_timeout));
5461546254635464546554665467546854695470547154725473547454755476547754785479548054815482548354845485548654875488548954905491549254935494549554965497549854995500550155025503550455055506550755085509551055115512551355145515551655175518551955205521552255235524552555265527552855295530
BC_ASSERT_TRUE(wait_for_list(coresList, &chloe->stat.number_of_LinphoneMessageSent, 1, 1000));
LinphoneChatMessage *marieLastMsg = marie->stat.last_received_chat_message;
if (!BC_ASSERT_PTR_NOT_NULL(marieLastMsg)) goto end;
BC_ASSERT_STRING_EQUAL(linphone_chat_message_get_text(marieLastMsg), chloeTextMessage);
LinphoneAddress *chloeAddr = linphone_address_new(linphone_core_get_identity(chloe->lc));
BC_ASSERT_TRUE(linphone_address_weak_equal(chloeAddr, linphone_chat_message_get_from_address(marieLastMsg)));
linphone_address_unref(chloeAddr);
// Check that the message has been delivered to Marie
BC_ASSERT_TRUE(wait_for_list(coresList, &chloe->stat.number_of_LinphoneMessageDelivered,
initialChloeStats.number_of_LinphoneMessageDeliveredToUser + 1,
liblinphone_tester_sip_timeout));
bctbx_list_t *participantsThatReceivedChloeMessage =
linphone_chat_message_get_participants_by_imdn_state(chloeMessage, LinphoneChatMessageStateDeliveredToUser);
if (BC_ASSERT_PTR_NOT_NULL(participantsThatReceivedChloeMessage)) {
BC_ASSERT_EQUAL((int)bctbx_list_size(participantsThatReceivedChloeMessage), 1, int, "%d");
bctbx_list_free_with_data(participantsThatReceivedChloeMessage,
(bctbx_list_free_func)linphone_participant_imdn_state_unref);
}
// Check that the message has been sent to Pauline
bctbx_list_t *participantsThatSentChloeMessage =
linphone_chat_message_get_participants_by_imdn_state(chloeMessage, LinphoneChatMessageStateDelivered);
if (BC_ASSERT_PTR_NOT_NULL(participantsThatSentChloeMessage)) {
BC_ASSERT_EQUAL((int)bctbx_list_size(participantsThatSentChloeMessage), 1, int, "%d");
bctbx_list_free_with_data(participantsThatSentChloeMessage,
(bctbx_list_free_func)linphone_participant_imdn_state_unref);
}
BC_ASSERT_PTR_NULL(
linphone_chat_message_get_participants_by_imdn_state(chloeMessage, LinphoneChatMessageStateNotDelivered));
// Marie marks the message as read
linphone_chat_room_mark_as_read(marieCr);
BC_ASSERT_FALSE(wait_for_list(coresList, &chloe->stat.number_of_LinphoneMessageDisplayed,
initialChloeStats.number_of_LinphoneMessageDisplayed + 1, 3000));
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneMessageSent, 0, 1000));
// Check that the message has beed displayed by Marie
bctbx_list_t *participantsThatDisplayedChloeMessage =
linphone_chat_message_get_participants_by_imdn_state(chloeMessage, LinphoneChatMessageStateDisplayed);
if (BC_ASSERT_PTR_NOT_NULL(participantsThatDisplayedChloeMessage)) {
BC_ASSERT_EQUAL((int)bctbx_list_size(participantsThatDisplayedChloeMessage), 1, int, "%d");
bctbx_list_free_with_data(participantsThatDisplayedChloeMessage,
(bctbx_list_free_func)linphone_participant_imdn_state_unref);
}
// Check that the message has been sent to Pauline
participantsThatSentChloeMessage =
linphone_chat_message_get_participants_by_imdn_state(chloeMessage, LinphoneChatMessageStateDelivered);
if (BC_ASSERT_PTR_NOT_NULL(participantsThatSentChloeMessage)) {
BC_ASSERT_EQUAL((int)bctbx_list_size(participantsThatSentChloeMessage), 1, int, "%d");
bctbx_list_free_with_data(participantsThatSentChloeMessage,
(bctbx_list_free_func)linphone_participant_imdn_state_unref);
}
BC_ASSERT_PTR_NULL(
linphone_chat_message_get_participants_by_imdn_state(chloeMessage, LinphoneChatMessageStateDeliveredToUser));
BC_ASSERT_PTR_NULL(
linphone_chat_message_get_participants_by_imdn_state(chloeMessage, LinphoneChatMessageStateNotDelivered));
// Check that the message state is Delivered
BC_ASSERT_TRUE(linphone_chat_message_get_state(chloeMessage) == LinphoneChatMessageStateDelivered);
// set appData will trigger update db
linphone_chat_message_set_appdata(chloeMessage, "");
// Check that the message has beed displayed by Marie
participantsThatDisplayedChloeMessage =
linphone_chat_message_get_participants_by_imdn_state(chloeMessage, LinphoneChatMessageStateDisplayed);
if (BC_ASSERT_PTR_NOT_NULL(participantsThatDisplayedChloeMessage)) {
BC_ASSERT_EQUAL((int)bctbx_list_size(participantsThatDisplayedChloeMessage), 1, int, "%d");
bctbx_list_free_with_data(participantsThatDisplayedChloeMessage,
(bctbx_list_free_func)linphone_participant_imdn_state_unref);
}
// Check that the message has been sent to Pauline
participantsThatSentChloeMessage =
5531553255335534553555365537553855395540554155425543554455455546554755485549555055515552555355545555555655575558555955605561556255635564556555665567556855695570557155725573557455755576557755785579558055815582558355845585558655875588558955905591559255935594559555965597559855995600
linphone_chat_message_get_participants_by_imdn_state(chloeMessage, LinphoneChatMessageStateDelivered);
if (BC_ASSERT_PTR_NOT_NULL(participantsThatSentChloeMessage)) {
BC_ASSERT_EQUAL((int)bctbx_list_size(participantsThatSentChloeMessage), 1, int, "%d");
bctbx_list_free_with_data(participantsThatSentChloeMessage,
(bctbx_list_free_func)linphone_participant_imdn_state_unref);
}
BC_ASSERT_PTR_NULL(
linphone_chat_message_get_participants_by_imdn_state(chloeMessage, LinphoneChatMessageStateDeliveredToUser));
BC_ASSERT_PTR_NULL(
linphone_chat_message_get_participants_by_imdn_state(chloeMessage, LinphoneChatMessageStateNotDelivered));
// Check that the message state is Delivered
BC_ASSERT_TRUE(linphone_chat_message_get_state(chloeMessage) == LinphoneChatMessageStateDelivered);
linphone_chat_message_unref(chloeMessage);
end:
// Clean db from chat room
if (marieCr) linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
if (chloeCr) linphone_core_manager_delete_chat_room(chloe, chloeCr, coresList);
if (paulineCr) linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
linphone_core_manager_destroy(chloe);
}
static void aggregated_imdn_for_group_chat_room_base(bool_t read_while_offline) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *chloe = linphone_core_manager_create("chloe_rc");
LinphoneCoreManager *chloe2 = linphone_core_manager_create("chloe_rc");
LinphoneChatRoom *marieCr = NULL, *paulineCr = NULL, *chloeCr = NULL, *chloe2Cr = NULL;
const LinphoneAddress *confAddr = NULL;
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
coresManagerList = bctbx_list_append(coresManagerList, chloe);
coresManagerList = bctbx_list_append(coresManagerList, chloe2);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(chloe->lc)));
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
stats initialChloeStats = chloe->stat;
stats initialChloe2Stats = chloe2->stat;
bctbx_list_t *chloeMessages = NULL, *chloe2Messages = NULL, *chloe2DisplayedMessages = NULL;
stats chloeMessagesStats = {0}, chloe2MessagesStats = {0}, chloe2DisplayedMessagesStats = {0};
int messageCount = 0;
// Enable IMDN
linphone_im_notif_policy_enable_all(linphone_core_get_im_notif_policy(marie->lc));
linphone_im_notif_policy_enable_all(linphone_core_get_im_notif_policy(pauline->lc));
linphone_im_notif_policy_enable_all(linphone_core_get_im_notif_policy(chloe->lc));
linphone_im_notif_policy_enable_all(linphone_core_get_im_notif_policy(chloe2->lc));
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
marieCr = create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject,
FALSE, LinphoneChatRoomEphemeralModeDeviceManaged);
if (!BC_ASSERT_PTR_NOT_NULL(marieCr)) goto end;
confAddr = linphone_chat_room_get_conference_address(marieCr);
if (!BC_ASSERT_PTR_NOT_NULL(confAddr)) goto end;
5601560256035604560556065607560856095610561156125613561456155616561756185619562056215622562356245625562656275628562956305631563256335634563556365637563856395640564156425643564456455646564756485649565056515652565356545655565656575658565956605661566256635664566556665667566856695670
// Check that the chat room is correctly created on Pauline's side and that the participants are added
paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats, confAddr, initialSubject,
2, FALSE);
if (!BC_ASSERT_PTR_NOT_NULL(paulineCr)) goto end;
// Check that the chat room is correctly created on Chloe's side and that the participants are added
chloeCr =
check_creation_chat_room_client_side(coresList, chloe, &initialChloeStats, confAddr, initialSubject, 2, FALSE);
if (!BC_ASSERT_PTR_NOT_NULL(chloeCr)) goto end;
// Check that the chat room is correctly created on Chloe2's side and that the participants are added
chloe2Cr = check_creation_chat_room_client_side(coresList, chloe2, &initialChloe2Stats, confAddr, initialSubject, 2,
FALSE);
if (!BC_ASSERT_PTR_NOT_NULL(chloe2Cr)) goto end;
// Chloe begins composing a message
const char *chloeTextMessage = "Hello";
const char *chloeTextMessage2 = "Long time no talk";
const char *chloeTextMessage3 = "How are you?";
LinphoneChatMessage *chloeMessage = _send_message(chloeCr, chloeTextMessage);
LinphoneChatMessage *chloeMessage2 = _send_message(chloeCr, chloeTextMessage2);
LinphoneChatMessage *chloeMessage3 = _send_message(chloeCr, chloeTextMessage3);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneMessageReceived,
initialMarieStats.number_of_LinphoneMessageReceived + 3,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageReceived,
initialPaulineStats.number_of_LinphoneMessageReceived + 3,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &chloe2->stat.number_of_LinphoneMessageReceived,
initialChloe2Stats.number_of_LinphoneMessageReceived + 3,
liblinphone_tester_sip_timeout));
LinphoneChatMessage *marieLastMsg = marie->stat.last_received_chat_message;
if (!BC_ASSERT_PTR_NOT_NULL(marieLastMsg)) goto end;
LinphoneChatMessage *chloe2LastMsg = chloe2->stat.last_received_chat_message;
if (!BC_ASSERT_PTR_NOT_NULL(chloe2LastMsg)) goto end;
BC_ASSERT_STRING_EQUAL(linphone_chat_message_get_text(marieLastMsg), chloeTextMessage3);
BC_ASSERT_STRING_EQUAL(linphone_chat_message_get_text(chloe2LastMsg), chloeTextMessage3);
LinphoneAddress *chloeAddr = linphone_address_new(linphone_core_get_identity(chloe->lc));
BC_ASSERT_TRUE(linphone_address_weak_equal(chloeAddr, linphone_chat_message_get_from_address(marieLastMsg)));
linphone_address_unref(chloeAddr);
// Mark as read on Chloe and Chloe2 should not impact the message status
linphone_chat_room_mark_as_read(chloeCr);
linphone_chat_room_mark_as_read(chloe2Cr);
// Mark the messages as read on Marie's sides
linphone_chat_room_mark_as_read(marieCr);
wait_for_list(coresList, 0, 1, 2000);
// Get Chloe2 messages and use them to set callbacks. Check callback status and messages status
chloe2Messages = liblinphone_tester_get_messages_and_states(
chloe2Cr, &messageCount, &chloe2MessagesStats); // Do not unref chloe2Messages to keep callbacks
if (!BC_ASSERT_PTR_NOT_NULL(chloe2Messages)) goto end;
for (bctbx_list_t *elem = chloe2Messages; elem != NULL; elem = bctbx_list_next(elem))
linphone_chat_message_cbs_set_msg_state_changed(
linphone_chat_message_get_callbacks((LinphoneChatMessage *)elem->data),
liblinphone_tester_chat_message_msg_state_changed);
// All participants didn't read messages yet (only Marie) : number_of_LinphoneMessageDisplayed == displayedCount
BC_ASSERT_EQUAL(chloe->stat.number_of_LinphoneMessageDisplayed,
initialChloeStats.number_of_LinphoneMessageDisplayed, int, "%d");
BC_ASSERT_EQUAL(chloe2->stat.number_of_LinphoneMessageDisplayed,
initialChloe2Stats.number_of_LinphoneMessageDisplayed, int, "%d");
BC_ASSERT_EQUAL(chloe2MessagesStats.number_of_LinphoneMessageDisplayed, 0, int, "%d");
BC_ASSERT_EQUAL(messageCount, 3, int, "%d");
// Mark the messages as read on Pauline's sides
if (read_while_offline) {
linphone_core_set_network_reachable(pauline->lc, FALSE);
linphone_chat_room_mark_as_read(paulineCr);
wait_for_list(coresList, 0, 1, 2000);
linphone_core_set_network_reachable(pauline->lc, TRUE);
} else {
5671567256735674567556765677567856795680568156825683568456855686568756885689569056915692569356945695569656975698569957005701570257035704570557065707570857095710571157125713571457155716571757185719572057215722572357245725572657275728572957305731573257335734573557365737573857395740
linphone_chat_room_mark_as_read(paulineCr);
}
// Messages have been read
BC_ASSERT_TRUE(wait_for_list(coresList, &chloe->stat.number_of_LinphoneMessageDisplayed,
initialChloeStats.number_of_LinphoneMessageDisplayed + 3,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &chloe2->stat.number_of_LinphoneMessageDisplayed,
initialChloe2Stats.number_of_LinphoneMessageDisplayed + 3,
liblinphone_tester_sip_timeout));
BC_ASSERT_EQUAL(chloe->stat.number_of_LinphoneMessageDeliveredToUser, 3, int, "%d"); // 3 for sending to chloe2
if (read_while_offline) {
wait_for_list(coresList, 0, 1, 2000); // To prevent memory leak
}
wait_for_list(coresList, 0, 1, 2000);
// Test internal data on Chloe2 and check consistency between callback and messages
chloe2DisplayedMessages =
liblinphone_tester_get_messages_and_states(chloe2Cr, &messageCount, &chloe2DisplayedMessagesStats);
BC_ASSERT_EQUAL(chloe2DisplayedMessagesStats.number_of_LinphoneMessageDisplayed, 3, int,
"%d"); // All messages have been read
BC_ASSERT_EQUAL(messageCount, 3, int, "%d");
// Test internal data on Chloe
chloeMessages = liblinphone_tester_get_messages_and_states(chloeCr, &messageCount, &chloeMessagesStats);
if (!BC_ASSERT_PTR_NOT_NULL(chloeMessages)) goto end;
BC_ASSERT_EQUAL(chloeMessagesStats.number_of_LinphoneMessageDisplayed, 3, int, "%d"); // All messages have been read
BC_ASSERT_EQUAL(messageCount, 3, int, "%d");
linphone_chat_message_unref(chloeMessage3);
linphone_chat_message_unref(chloeMessage2);
linphone_chat_message_unref(chloeMessage);
end:
if (chloeMessages) bctbx_list_free_with_data(chloeMessages, (bctbx_list_free_func)linphone_chat_message_unref);
if (chloe2Messages) bctbx_list_free_with_data(chloe2Messages, (bctbx_list_free_func)linphone_chat_message_unref);
if (chloe2DisplayedMessages)
bctbx_list_free_with_data(chloe2DisplayedMessages, (bctbx_list_free_func)linphone_chat_message_unref);
// Clean db from chat room
if (marieCr) linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
if (chloeCr) linphone_core_manager_delete_chat_room(chloe, chloeCr, coresList);
if (chloe2Cr) linphone_core_manager_delete_chat_room(chloe2, chloe2Cr, coresList);
if (paulineCr) linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
linphone_core_manager_destroy(chloe);
linphone_core_manager_destroy(chloe2);
}
static void aggregated_imdn_for_group_chat_room(void) {
aggregated_imdn_for_group_chat_room_base(FALSE);
}
static void aggregated_imdn_for_group_chat_room_read_while_offline(void) {
aggregated_imdn_for_group_chat_room_base(TRUE);
}
static void imdn_sent_from_db_state(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *chloe = linphone_core_manager_create("chloe_rc");
LinphoneChatRoom *marieCr = NULL, *paulineCr = NULL, *chloeCr = NULL;
LinphoneAddress *confAddr = NULL;
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
5741574257435744574557465747574857495750575157525753575457555756575757585759576057615762576357645765576657675768576957705771577257735774577557765777577857795780578157825783578457855786578757885789579057915792579357945795579657975798579958005801580258035804580558065807580858095810
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
coresManagerList = bctbx_list_append(coresManagerList, chloe);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(chloe->lc)));
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
stats initialChloeStats = chloe->stat;
time_t initialTime = ms_time(NULL);
// Enable IMDN except for Marie
linphone_im_notif_policy_clear(linphone_core_get_im_notif_policy(marie->lc));
linphone_im_notif_policy_enable_all(linphone_core_get_im_notif_policy(pauline->lc));
linphone_im_notif_policy_enable_all(linphone_core_get_im_notif_policy(chloe->lc));
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
marieCr = create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject,
FALSE, LinphoneChatRoomEphemeralModeDeviceManaged);
if (!BC_ASSERT_PTR_NOT_NULL(marieCr)) goto end;
confAddr = (LinphoneAddress *)linphone_chat_room_get_conference_address(marieCr);
if (!BC_ASSERT_PTR_NOT_NULL(confAddr)) goto end;
confAddr = linphone_address_clone(confAddr);
// Check that the chat room is correctly created on Pauline's side and that the participants are added
paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats, confAddr, initialSubject,
2, FALSE);
if (!BC_ASSERT_PTR_NOT_NULL(paulineCr)) goto end;
// Check that the chat room is correctly created on Chloe's side and that the participants are added
chloeCr =
check_creation_chat_room_client_side(coresList, chloe, &initialChloeStats, confAddr, initialSubject, 2, FALSE);
if (!BC_ASSERT_PTR_NOT_NULL(chloeCr)) goto end;
// Chloe begins composing a message
const char *chloeTextMessage = "Hello";
LinphoneChatMessage *chloeMessage = _send_message(chloeCr, chloeTextMessage);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneMessageReceived,
initialMarieStats.number_of_LinphoneMessageReceived + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageReceived,
initialPaulineStats.number_of_LinphoneMessageReceived + 1,
liblinphone_tester_sip_timeout));
LinphoneChatMessage *marieLastMsg = marie->stat.last_received_chat_message;
if (!BC_ASSERT_PTR_NOT_NULL(marieLastMsg)) goto end;
BC_ASSERT_STRING_EQUAL(linphone_chat_message_get_text(marieLastMsg), chloeTextMessage);
LinphoneAddress *chloeAddr = linphone_address_new(linphone_core_get_identity(chloe->lc));
BC_ASSERT_TRUE(linphone_address_weak_equal(chloeAddr, linphone_chat_message_get_from_address(marieLastMsg)));
linphone_address_unref(chloeAddr);
// Check that the message is not globally marked as delivered to user since Marie do not notify its delivery
BC_ASSERT_FALSE(wait_for_list(coresList, &chloe->stat.number_of_LinphoneMessageDeliveredToUser,
initialChloeStats.number_of_LinphoneMessageDeliveredToUser + 1, 3000));
// Restart Marie's core with IMDN enabled so that delivery notification is sent when chat room is loaded from DB
coresList = bctbx_list_remove(coresList, marie->lc);
linphone_core_manager_reinit(marie);
bctbx_list_t *tmpCoresManagerList = bctbx_list_append(NULL, marie);
bctbx_list_t *tmpCoresList = init_core_for_conference(tmpCoresManagerList);
bctbx_list_free(tmpCoresManagerList);
coresList = bctbx_list_concat(coresList, tmpCoresList);
linphone_im_notif_policy_enable_all(linphone_core_get_im_notif_policy(marie->lc));
linphone_core_manager_start(marie, TRUE);
char *marieIdentity = linphone_core_get_device_identity(marie->lc);
LinphoneAddress *marieAddr = linphone_address_new(marieIdentity);
bctbx_free(marieIdentity);
5811581258135814581558165817581858195820582158225823582458255826582758285829583058315832583358345835583658375838583958405841584258435844584558465847584858495850585158525853585458555856585758585859586058615862586358645865586658675868586958705871587258735874587558765877587858795880
marieCr = linphone_core_find_chat_room(marie->lc, confAddr, marieAddr);
linphone_address_unref(marieAddr);
// Check that the message has been delivered to Marie and Pauline
BC_ASSERT_TRUE(wait_for_list(coresList, &chloe->stat.number_of_LinphoneMessageDeliveredToUser,
initialChloeStats.number_of_LinphoneMessageDeliveredToUser + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_PTR_NULL(
linphone_chat_message_get_participants_by_imdn_state(chloeMessage, LinphoneChatMessageStateDisplayed));
bctbx_list_t *participantsThatReceivedChloeMessage =
linphone_chat_message_get_participants_by_imdn_state(chloeMessage, LinphoneChatMessageStateDeliveredToUser);
if (BC_ASSERT_PTR_NOT_NULL(participantsThatReceivedChloeMessage)) {
BC_ASSERT_EQUAL((int)bctbx_list_size(participantsThatReceivedChloeMessage), 2, int, "%d");
for (bctbx_list_t *item = participantsThatReceivedChloeMessage; item; item = bctbx_list_next(item)) {
LinphoneParticipantImdnState *state = (LinphoneParticipantImdnState *)bctbx_list_get_data(item);
BC_ASSERT_GREATER((int)linphone_participant_imdn_state_get_state_change_time(state), (int)initialTime, int,
"%d");
BC_ASSERT_EQUAL(linphone_participant_imdn_state_get_state(state), LinphoneChatMessageStateDeliveredToUser,
int, "%d");
BC_ASSERT_PTR_NOT_NULL(linphone_participant_imdn_state_get_participant(state));
}
bctbx_list_free_with_data(participantsThatReceivedChloeMessage,
(bctbx_list_free_func)linphone_participant_imdn_state_unref);
}
BC_ASSERT_PTR_NULL(
linphone_chat_message_get_participants_by_imdn_state(chloeMessage, LinphoneChatMessageStateDelivered));
BC_ASSERT_PTR_NULL(
linphone_chat_message_get_participants_by_imdn_state(chloeMessage, LinphoneChatMessageStateNotDelivered));
linphone_chat_message_unref(chloeMessage);
end:
if (confAddr) linphone_address_unref(confAddr);
// Clean db from chat room
if (marieCr) linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
if (chloeCr) linphone_core_manager_delete_chat_room(chloe, chloeCr, coresList);
if (paulineCr) linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
linphone_core_manager_destroy(chloe);
}
static void find_one_to_one_chat_room(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *chloe = linphone_core_manager_create("chloe_rc");
LinphoneChatRoom *marieCr = NULL, *paulineCr = NULL, *chloeCr = NULL, *marieOneToOneCr = NULL;
const LinphoneAddress *confAddr = NULL;
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
coresManagerList = bctbx_list_append(coresManagerList, chloe);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(chloe->lc)));
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
stats initialChloeStats = chloe->stat;
// Only to be used in linphone_core_find_one_to_one_chatroom(...);
const LinphoneAddress *marieAddr =
linphone_proxy_config_get_contact(linphone_core_get_default_proxy_config(marie->lc));
const LinphoneAddress *paulineAddr =
5881588258835884588558865887588858895890589158925893589458955896589758985899590059015902590359045905590659075908590959105911591259135914591559165917591859195920592159225923592459255926592759285929593059315932593359345935593659375938593959405941594259435944594559465947594859495950
linphone_proxy_config_get_identity_address(linphone_core_get_default_proxy_config(pauline->lc));
LinphoneChatMessage *basicMessage = NULL;
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
marieCr = create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject,
FALSE, LinphoneChatRoomEphemeralModeDeviceManaged);
if (!BC_ASSERT_PTR_NOT_NULL(marieCr)) goto end;
confAddr = linphone_chat_room_get_conference_address(marieCr);
if (!BC_ASSERT_PTR_NOT_NULL(confAddr)) goto end;
// Check that the chat room is correctly created on Pauline's side and that the participants are added
paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats, confAddr, initialSubject,
2, FALSE);
if (!BC_ASSERT_PTR_NOT_NULL(paulineCr)) goto end;
// Check that the chat room is correctly created on Chloe's side and that the participants are added
chloeCr =
check_creation_chat_room_client_side(coresList, chloe, &initialChloeStats, confAddr, initialSubject, 2, FALSE);
if (!BC_ASSERT_PTR_NOT_NULL(chloeCr)) goto end;
// Chloe leave the chat room
linphone_chat_room_leave(chloeCr);
BC_ASSERT_TRUE(wait_for_list(coresList, &chloe->stat.number_of_LinphoneConferenceStateTerminationPending,
initialChloeStats.number_of_LinphoneConferenceStateTerminationPending + 1, 100));
BC_ASSERT_TRUE(wait_for_list(coresList, &chloe->stat.number_of_LinphoneConferenceStateTerminated,
initialChloeStats.number_of_LinphoneConferenceStateTerminated + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_participants_removed,
initialPaulineStats.number_of_participants_removed + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_participants_removed,
initialMarieStats.number_of_participants_removed + 1, liblinphone_tester_sip_timeout));
LinphoneChatRoom *oneToOneChatRoom = linphone_core_find_one_to_one_chat_room(marie->lc, marieAddr, paulineAddr);
BC_ASSERT_PTR_NULL(oneToOneChatRoom);
// Marie create a one to one chat room with Pauline
participantsAddresses = NULL;
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
initialMarieStats = marie->stat;
initialPaulineStats = pauline->stat;
marieOneToOneCr = create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses,
"one to one", FALSE, LinphoneChatRoomEphemeralModeDeviceManaged);
if (!BC_ASSERT_PTR_NOT_NULL(marieOneToOneCr)) goto end;
confAddr = linphone_chat_room_get_conference_address(marieOneToOneCr);
LinphoneChatRoom *paulineOneToOneCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats,
confAddr, "one to one", 1, FALSE);
// Marie creates a basic chat room with Pauline
participantsAddresses = NULL;
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
LinphoneChatRoomParams *params = linphone_core_create_default_chat_room_params(marie->lc);
linphone_chat_room_params_set_backend(params, LinphoneChatRoomBackendBasic);
linphone_chat_room_params_enable_group(params, FALSE);
LinphoneChatRoom *basicCR = linphone_core_create_chat_room_6(marie->lc, params, marieAddr, participantsAddresses);
linphone_chat_room_params_unref(params);
// Check it returns the One-To-One chat room (flexisip based)
oneToOneChatRoom = linphone_core_find_one_to_one_chat_room(marie->lc, marieAddr, paulineAddr);
BC_ASSERT_PTR_NOT_NULL(oneToOneChatRoom);
BC_ASSERT_PTR_EQUAL(oneToOneChatRoom, marieOneToOneCr);
// Check it returns the Basic chat room
oneToOneChatRoom = linphone_core_search_chat_room(marie->lc, NULL, marieAddr, paulineAddr, NULL);
BC_ASSERT_PTR_NOT_NULL(oneToOneChatRoom);
BC_ASSERT_PTR_EQUAL(oneToOneChatRoom, basicCR);
5951595259535954595559565957595859595960596159625963596459655966596759685969597059715972597359745975597659775978597959805981598259835984598559865987598859895990599159925993599459955996599759985999600060016002600360046005600660076008600960106011601260136014601560166017601860196020
// Check it returns the Basic chat room
params = linphone_core_create_default_chat_room_params(marie->lc);
linphone_chat_room_params_set_backend(params, LinphoneChatRoomBackendBasic);
oneToOneChatRoom = linphone_core_search_chat_room(marie->lc, params, marieAddr, NULL, participantsAddresses);
BC_ASSERT_PTR_NOT_NULL(oneToOneChatRoom);
BC_ASSERT_PTR_EQUAL(oneToOneChatRoom, basicCR);
// Check it returns the One-To-One chat room (flexisip based)
linphone_chat_room_params_set_backend(params, LinphoneChatRoomBackendFlexisipChat);
oneToOneChatRoom = linphone_core_search_chat_room(marie->lc, params, marieAddr, NULL, participantsAddresses);
BC_ASSERT_PTR_NOT_NULL(oneToOneChatRoom);
BC_ASSERT_PTR_EQUAL(oneToOneChatRoom, marieOneToOneCr);
bctbx_list_free_with_data(participantsAddresses, (bctbx_list_free_func)linphone_address_unref);
participantsAddresses = NULL;
linphone_chat_room_params_unref(params);
// Clean the db
linphone_core_manager_delete_chat_room(marie, marieOneToOneCr, coresList);
linphone_core_manager_delete_chat_room(pauline, paulineOneToOneCr, coresList);
marieOneToOneCr = NULL;
paulineOneToOneCr = NULL;
// Check cleaning went well
oneToOneChatRoom = linphone_core_find_one_to_one_chat_room(marie->lc, marieAddr, paulineAddr);
BC_ASSERT_PTR_NOT_NULL(oneToOneChatRoom);
BC_ASSERT_PTR_EQUAL(oneToOneChatRoom, basicCR);
if (basicCR) linphone_chat_room_unref(basicCR);
end:
// Clean db from chat room
if (basicMessage) linphone_chat_message_unref(basicMessage);
if (marieOneToOneCr) linphone_core_manager_delete_chat_room(marie, marieOneToOneCr, coresList);
if (marieCr) linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
if (chloeCr) linphone_core_manager_delete_chat_room(chloe, chloeCr, coresList);
if (paulineCr) linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
linphone_core_manager_destroy(chloe);
}
static void exhume_one_to_one_chat_room_1(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneChatRoom *marieOneToOneCr = NULL, *paulineOneToOneCr = NULL;
LinphoneAddress *confAddr = NULL, *exhumedConfAddr = NULL;
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
initialMarieStats = marie->stat;
initialPaulineStats = pauline->stat;
marieOneToOneCr = create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses,
"one to one", FALSE, LinphoneChatRoomEphemeralModeDeviceManaged);
if (!BC_ASSERT_PTR_NOT_NULL(marieOneToOneCr)) goto end;
confAddr = linphone_address_clone((LinphoneAddress *)linphone_chat_room_get_conference_address(marieOneToOneCr));
paulineOneToOneCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats, confAddr,
"one to one", 1, FALSE);
6021602260236024602560266027602860296030603160326033603460356036603760386039604060416042604360446045604660476048604960506051605260536054605560566057605860596060606160626063606460656066606760686069607060716072607360746075607660776078607960806081608260836084608560866087608860896090
LinphoneChatMessage *message =
linphone_chat_room_create_message_from_utf8(paulineOneToOneCr, "Do. Or do not. There is no try.");
linphone_chat_message_send(message);
BC_ASSERT_TRUE(
wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageSent, 1, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(
wait_for_list(coresList, &marie->stat.number_of_LinphoneMessageReceived, 1, liblinphone_tester_sip_timeout));
linphone_chat_message_unref(message);
BC_ASSERT_FALSE(linphone_chat_room_is_read_only(marieOneToOneCr));
BC_ASSERT_FALSE(linphone_chat_room_is_read_only(paulineOneToOneCr));
if (marieOneToOneCr) {
linphone_core_manager_delete_chat_room(marie, marieOneToOneCr, coresList);
BC_ASSERT_TRUE(wait_for_until(marie->lc, pauline->lc, &marie->stat.number_of_LinphoneConferenceStateTerminated,
1, liblinphone_tester_sip_timeout));
/* The chatroom from Pauline is expected to terminate as well */
BC_ASSERT_TRUE(wait_for_until(marie->lc, pauline->lc,
&pauline->stat.number_of_LinphoneConferenceStateTerminated, 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_FALSE(linphone_chat_room_is_read_only(paulineOneToOneCr));
bctbx_list_t *participants = linphone_chat_room_get_participants(paulineOneToOneCr);
BC_ASSERT_EQUAL((int)bctbx_list_size(participants), 1, int, "%d");
bctbx_list_free_with_data(participants, (bctbx_list_free_func)linphone_participant_unref);
LinphoneChatMessage *exhume_message =
linphone_chat_room_create_message_from_utf8(paulineOneToOneCr, "No. I am your father.");
linphone_chat_message_send(exhume_message);
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneConferenceStateCreated, 2,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(
wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageSent, 2, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneConferenceStateCreated, 2,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneMessageReceived, 2,
liblinphone_tester_sip_timeout));
linphone_chat_message_unref(exhume_message);
exhumedConfAddr =
linphone_address_ref((LinphoneAddress *)linphone_chat_room_get_conference_address(paulineOneToOneCr));
BC_ASSERT_PTR_NOT_NULL(exhumedConfAddr);
int pauline_messages = linphone_chat_room_get_history_size(paulineOneToOneCr);
BC_ASSERT_EQUAL(pauline_messages, 2, int, "%d");
if (exhumedConfAddr) {
BC_ASSERT_FALSE(linphone_address_weak_equal(confAddr, exhumedConfAddr));
marieOneToOneCr = check_creation_chat_room_client_side(coresList, marie, &initialMarieStats,
exhumedConfAddr, "one to one", 1, FALSE);
BC_ASSERT_PTR_NOT_NULL(marieOneToOneCr);
if (marieOneToOneCr) {
int marie_messages = linphone_chat_room_get_history_size(marieOneToOneCr);
BC_ASSERT_EQUAL(marie_messages, 1, int, "%d");
LinphoneChatMessage *exhume_answer_message =
linphone_chat_room_create_message_from_utf8(marieOneToOneCr, "Nooooooooooooo !");
linphone_chat_message_send(exhume_answer_message);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneMessageSent, 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageReceived, 1,
liblinphone_tester_sip_timeout));
linphone_chat_message_unref(exhume_answer_message);
}
}
linphone_config_set_int(linphone_core_get_config(pauline->lc), "misc", "hide_empty_chat_rooms", 0);
linphone_config_set_int(linphone_core_get_config(pauline->lc), "misc", "hide_chat_rooms_from_removed_proxies",
0);
6091609260936094609560966097609860996100610161026103610461056106610761086109611061116112611361146115611661176118611961206121612261236124612561266127612861296130613161326133613461356136613761386139614061416142614361446145614661476148614961506151615261536154615561566157615861596160
const bctbx_list_t *pauline_chat_rooms = linphone_core_get_chat_rooms(pauline->lc);
BC_ASSERT_EQUAL((int)bctbx_list_size(pauline_chat_rooms), 1, int, "%d");
linphone_config_set_int(linphone_core_get_config(marie->lc), "misc", "hide_empty_chat_rooms", 0);
linphone_config_set_int(linphone_core_get_config(pauline->lc), "misc", "hide_chat_rooms_from_removed_proxies",
0);
const bctbx_list_t *marie_chat_rooms = linphone_core_get_chat_rooms(marie->lc);
BC_ASSERT_EQUAL((int)bctbx_list_size(marie_chat_rooms), 1, int, "%d");
BC_ASSERT_FALSE(linphone_chat_room_is_read_only(marieOneToOneCr));
BC_ASSERT_FALSE(linphone_chat_room_is_read_only(paulineOneToOneCr));
}
end:
if (confAddr) linphone_address_unref(confAddr);
if (exhumedConfAddr) linphone_address_unref(exhumedConfAddr);
if (marieOneToOneCr) linphone_core_manager_delete_chat_room(marie, marieOneToOneCr, coresList);
if (paulineOneToOneCr) linphone_core_manager_delete_chat_room(pauline, paulineOneToOneCr, coresList);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
}
static void exhume_one_to_one_chat_room_2(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneChatRoom *marieOneToOneCr = NULL, *paulineOneToOneCr = NULL;
LinphoneAddress *confAddr = NULL, *exhumedConfAddr = NULL;
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
initialMarieStats = marie->stat;
initialPaulineStats = pauline->stat;
marieOneToOneCr = create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses,
"one to one", FALSE, LinphoneChatRoomEphemeralModeDeviceManaged);
if (!BC_ASSERT_PTR_NOT_NULL(marieOneToOneCr)) goto end;
confAddr = linphone_address_clone((LinphoneAddress *)linphone_chat_room_get_conference_address(marieOneToOneCr));
paulineOneToOneCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats, confAddr,
"one to one", 1, FALSE);
LinphoneChatMessage *message =
linphone_chat_room_create_message_from_utf8(paulineOneToOneCr, "Help me, Obi-Wan Kenobi. You’re my only hope.");
linphone_chat_message_send(message);
BC_ASSERT_TRUE(
wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageSent, 1, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(
wait_for_list(coresList, &marie->stat.number_of_LinphoneMessageReceived, 1, liblinphone_tester_sip_timeout));
linphone_chat_message_unref(message);
BC_ASSERT_FALSE(linphone_chat_room_is_read_only(marieOneToOneCr));
BC_ASSERT_FALSE(linphone_chat_room_is_read_only(paulineOneToOneCr));
if (marieOneToOneCr) {
linphone_core_manager_delete_chat_room(marie, marieOneToOneCr, coresList);
BC_ASSERT_TRUE(wait_for_until(marie->lc, pauline->lc, &marie->stat.number_of_LinphoneConferenceStateTerminated,
1, liblinphone_tester_sip_timeout));
/* The chatroom from Pauline is expected to terminate as well */
BC_ASSERT_TRUE(wait_for_until(marie->lc, pauline->lc,
6161616261636164616561666167616861696170617161726173617461756176617761786179618061816182618361846185618661876188618961906191619261936194619561966197619861996200620162026203620462056206620762086209621062116212621362146215621662176218621962206221622262236224622562266227622862296230
&pauline->stat.number_of_LinphoneConferenceStateTerminated, 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_FALSE(linphone_chat_room_is_read_only(paulineOneToOneCr));
participantsAddresses = NULL;
initialMarieStats = marie->stat;
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
marieOneToOneCr = create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses,
"one to one", FALSE, LinphoneChatRoomEphemeralModeDeviceManaged);
wait_for_until(marie->lc, NULL, &marie->stat.number_of_LinphoneConferenceStateCreated, 2, 5000);
if (!BC_ASSERT_PTR_NOT_NULL(marieOneToOneCr)) goto end;
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneConferenceStateCreated, 2,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneConferenceStateCreated, 2,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneChatRoomConferenceJoined, 2,
liblinphone_tester_sip_timeout));
exhumedConfAddr =
linphone_address_clone((LinphoneAddress *)linphone_chat_room_get_conference_address(marieOneToOneCr));
BC_ASSERT_PTR_NOT_NULL(exhumedConfAddr);
if (exhumedConfAddr) {
BC_ASSERT_FALSE(linphone_address_weak_equal(confAddr, exhumedConfAddr));
LinphoneAddress *paulineNewConfAddr =
linphone_address_ref((LinphoneAddress *)linphone_chat_room_get_conference_address(paulineOneToOneCr));
BC_ASSERT_FALSE(linphone_address_weak_equal(confAddr, paulineNewConfAddr));
BC_ASSERT_TRUE(linphone_address_weak_equal(exhumedConfAddr, paulineNewConfAddr));
if (paulineNewConfAddr) linphone_address_unref(paulineNewConfAddr);
LinphoneChatMessage *exhume_message =
linphone_chat_room_create_message_from_utf8(marieOneToOneCr, "I find your lack of faith disturbing.");
linphone_chat_message_send(exhume_message);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneMessageSent, 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageReceived, 1,
liblinphone_tester_sip_timeout));
linphone_chat_message_unref(exhume_message);
int pauline_messages = linphone_chat_room_get_history_size(paulineOneToOneCr);
BC_ASSERT_EQUAL(pauline_messages, 2, int, "%d");
int marie_messages = linphone_chat_room_get_history_size(marieOneToOneCr);
BC_ASSERT_EQUAL(marie_messages, 1, int, "%d");
LinphoneChatRoom *paulineOneToOneCr2 = check_creation_chat_room_client_side(
coresList, pauline, &initialPaulineStats, exhumedConfAddr, "one to one", 1, FALSE);
BC_ASSERT_PTR_NOT_NULL(paulineOneToOneCr2);
if (paulineOneToOneCr2) {
int pauline_messages = linphone_chat_room_get_history_size(paulineOneToOneCr2);
BC_ASSERT_EQUAL(pauline_messages, 2, int, "%d");
LinphoneChatMessage *exhume_answer_message = linphone_chat_room_create_message_from_utf8(
paulineOneToOneCr2, "Your focus determines your reality.");
linphone_chat_message_send(exhume_answer_message);
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageSent, 2,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneMessageReceived, 2,
liblinphone_tester_sip_timeout));
linphone_chat_message_unref(exhume_answer_message);
}
}
linphone_config_set_int(linphone_core_get_config(pauline->lc), "misc", "hide_empty_chat_rooms", 0);
linphone_config_set_int(linphone_core_get_config(pauline->lc), "misc", "hide_chat_rooms_from_removed_proxies",
0);
const bctbx_list_t *pauline_chat_rooms = linphone_core_get_chat_rooms(pauline->lc);
BC_ASSERT_EQUAL((int)bctbx_list_size(pauline_chat_rooms), 1, int, "%d");
6231623262336234623562366237623862396240624162426243624462456246624762486249625062516252625362546255625662576258625962606261626262636264626562666267626862696270627162726273627462756276627762786279628062816282628362846285628662876288628962906291629262936294629562966297629862996300
linphone_config_set_int(linphone_core_get_config(marie->lc), "misc", "hide_empty_chat_rooms", 0);
linphone_config_set_int(linphone_core_get_config(pauline->lc), "misc", "hide_chat_rooms_from_removed_proxies",
0);
const bctbx_list_t *marie_chat_rooms = linphone_core_get_chat_rooms(marie->lc);
BC_ASSERT_EQUAL((int)bctbx_list_size(marie_chat_rooms), 1, int, "%d");
BC_ASSERT_FALSE(linphone_chat_room_is_read_only(marieOneToOneCr));
BC_ASSERT_FALSE(linphone_chat_room_is_read_only(paulineOneToOneCr));
}
end:
if (confAddr) linphone_address_unref(confAddr);
if (exhumedConfAddr) linphone_address_unref(exhumedConfAddr);
if (marieOneToOneCr) linphone_core_manager_delete_chat_room(marie, marieOneToOneCr, coresList);
if (paulineOneToOneCr) linphone_core_manager_delete_chat_room(pauline, paulineOneToOneCr, coresList);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
}
static void linphone_tester_chat_room_exhumed(LinphoneCore *core, BCTBX_UNUSED(LinphoneChatRoom *room)) {
stats *counters;
counters = get_stats(core);
counters->number_of_LinphoneChatRoomExhumed++;
}
static void exhume_one_to_one_chat_room_3_base(bool_t core_restart) {
// WARNING: some waits are supposed to timeout in this test: the BC_ASSER_FALSE(wait_for...), do not increase the
// value or it triggers a timeout on the server side
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *pauline2 = NULL;
LinphoneChatRoom *marieOneToOneCr = NULL, *pauline2OneToOneCr = NULL, *paulineOneToOneCr = NULL;
int marie_messages = 0, pauline_messages = 0, pauline2_messages = 0;
LinphoneAddress *confAddr = NULL, *exhumedConfAddr = NULL;
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
char *conference_address_str = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
const char *initialSubject = "one to one";
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
initialMarieStats = marie->stat;
initialPaulineStats = pauline->stat;
marieOneToOneCr = create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses,
initialSubject, FALSE, LinphoneChatRoomEphemeralModeDeviceManaged);
if (!BC_ASSERT_PTR_NOT_NULL(marieOneToOneCr)) goto end;
confAddr = linphone_address_ref((LinphoneAddress *)linphone_chat_room_get_conference_address(marieOneToOneCr));
BC_ASSERT_PTR_NOT_NULL(confAddr);
conference_address_str = (confAddr) ? linphone_address_as_string(confAddr) : ms_strdup("<unknown>");
paulineOneToOneCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats, confAddr,
initialSubject, 1, FALSE);
LinphoneChatMessage *message =
linphone_chat_room_create_message_from_utf8(paulineOneToOneCr, "Hasta la vista, baby.");
linphone_chat_message_send(message);
BC_ASSERT_TRUE(
6301630263036304630563066307630863096310631163126313631463156316631763186319632063216322632363246325632663276328632963306331633263336334633563366337633863396340634163426343634463456346634763486349635063516352635363546355635663576358635963606361636263636364636563666367636863696370
wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageSent, 1, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(
wait_for_list(coresList, &marie->stat.number_of_LinphoneMessageReceived, 1, liblinphone_tester_sip_timeout));
linphone_chat_message_unref(message);
marie_messages = linphone_chat_room_get_history_size(marieOneToOneCr);
BC_ASSERT_EQUAL(marie_messages, 1, int, "%d");
pauline_messages = linphone_chat_room_get_history_size(paulineOneToOneCr);
BC_ASSERT_EQUAL(pauline_messages, 1, int, "%d");
// Pauline goes offline
int dummy = 0;
wait_for_list(coresList, &dummy, 1, 5000); // Ensures 200 OK of the NOTIFY has been ACK'ed
ms_message("%s goes offline", linphone_core_get_identity(pauline->lc));
linphone_core_set_network_reachable(pauline->lc, FALSE);
wait_for_list(coresList, &dummy, 1, 2000);
BC_ASSERT_FALSE(linphone_chat_room_is_read_only(marieOneToOneCr));
BC_ASSERT_FALSE(linphone_chat_room_is_read_only(paulineOneToOneCr));
if (marieOneToOneCr) {
pauline2 = linphone_core_manager_create("pauline_rc");
stats initialPauline2Stats = pauline2->stat;
coresManagerList = bctbx_list_append(coresManagerList, pauline2);
bctbx_list_t *tmpCoresManagerList = bctbx_list_append(NULL, pauline2);
bctbx_list_t *tmpCoresList = init_core_for_conference(tmpCoresManagerList);
start_core_for_conference(tmpCoresManagerList);
bctbx_list_free(tmpCoresManagerList);
coresList = bctbx_list_concat(coresList, tmpCoresList);
pauline2OneToOneCr = check_creation_chat_room_client_side(coresList, pauline2, &initialPauline2Stats, confAddr,
initialSubject, 1, FALSE);
BC_ASSERT_PTR_NOT_NULL(pauline2OneToOneCr);
if (!pauline2OneToOneCr) goto end;
BC_ASSERT_FALSE(wait_for_list(coresList, &pauline2->stat.number_of_LinphoneMessageReceived, 2, 5000));
LinphoneChatMessage *offline_message =
linphone_chat_room_create_message_from_utf8(marieOneToOneCr, "I'll be back.");
linphone_chat_message_send(offline_message);
BC_ASSERT_TRUE(
wait_for_list(coresList, &marie->stat.number_of_LinphoneMessageSent, 1, liblinphone_tester_sip_timeout));
BC_ASSERT_FALSE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageReceived, 1, 5000));
linphone_chat_message_unref(offline_message);
// The other device using Pauline's account received the message as she was online
pauline2_messages = linphone_chat_room_get_history_size(pauline2OneToOneCr);
BC_ASSERT_EQUAL(pauline2_messages, 1, int, "%d");
marie_messages = linphone_chat_room_get_history_size(marieOneToOneCr);
BC_ASSERT_EQUAL(marie_messages, 2, int, "%d");
pauline_messages = linphone_chat_room_get_history_size(paulineOneToOneCr);
BC_ASSERT_EQUAL(pauline_messages, 1, int, "%d");
ms_message("%s is deleting chat room %s", linphone_core_get_identity(marie->lc), conference_address_str);
linphone_core_manager_delete_chat_room(marie, marieOneToOneCr, coresList);
BC_ASSERT_TRUE(wait_for_until(marie->lc, pauline->lc, &marie->stat.number_of_LinphoneConferenceStateTerminated,
1, liblinphone_tester_sip_timeout));
/* The chatroom from Pauline won't be terminated as it is offline */
BC_ASSERT_FALSE(wait_for_until(marie->lc, pauline->lc,
&pauline->stat.number_of_LinphoneConferenceStateTerminated, 1, 5000));
participantsAddresses = NULL;
initialMarieStats = marie->stat;
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
ms_message("%s is exhuming chat room %s", linphone_core_get_identity(marie->lc), conference_address_str);
6371637263736374637563766377637863796380638163826383638463856386638763886389639063916392639363946395639663976398639964006401640264036404640564066407640864096410641164126413641464156416641764186419642064216422642364246425642664276428642964306431643264336434643564366437643864396440
marieOneToOneCr =
create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject,
FALSE, LinphoneChatRoomEphemeralModeDeviceManaged);
wait_for_until(marie->lc, NULL, &marie->stat.number_of_LinphoneConferenceStateCreated, 2,
liblinphone_tester_sip_timeout);
if (!BC_ASSERT_PTR_NOT_NULL(marieOneToOneCr)) goto end;
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneConferenceStateCreated, 2,
liblinphone_tester_sip_timeout));
BC_ASSERT_FALSE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneConferenceStateCreated, 2, 5000));
BC_ASSERT_FALSE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneChatRoomConferenceJoined, 2, 5000));
exhumedConfAddr =
linphone_address_ref((LinphoneAddress *)linphone_chat_room_get_conference_address(marieOneToOneCr));
BC_ASSERT_PTR_NOT_NULL(exhumedConfAddr);
if (exhumedConfAddr) {
LinphoneChatMessage *exhume_message =
linphone_chat_room_create_message_from_utf8(marieOneToOneCr, "I'm back.");
linphone_chat_message_send(exhume_message);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneMessageSent, 2,
liblinphone_tester_sip_timeout));
BC_ASSERT_FALSE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageReceived, 2, 5000));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline2->stat.number_of_LinphoneMessageReceived, 2,
liblinphone_tester_sip_timeout));
marie_messages = linphone_chat_room_get_history_size(marieOneToOneCr);
BC_ASSERT_EQUAL(marie_messages, 1, int, "%d");
pauline_messages = linphone_chat_room_get_history_size(paulineOneToOneCr);
BC_ASSERT_EQUAL(pauline_messages, 1, int, "%d");
pauline2_messages = linphone_chat_room_get_history_size(pauline2OneToOneCr);
BC_ASSERT_EQUAL(pauline2_messages, 2, int, "%d");
linphone_chat_message_unref(exhume_message);
if (core_restart) {
ms_message("%s is restarting its core", linphone_core_get_identity(pauline->lc));
coresList = bctbx_list_remove(coresList, pauline->lc);
linphone_core_manager_reinit(pauline);
// Make sure conference factory URI is preserved
LinphoneProxyConfig *lpc = linphone_core_get_default_proxy_config(pauline->lc);
linphone_proxy_config_edit(lpc);
linphone_proxy_config_set_conference_factory_uri(lpc, sFactoryUri);
linphone_proxy_config_done(lpc);
bctbx_list_t *tmpCoresManagerList = bctbx_list_append(NULL, pauline);
init_core_for_conference(tmpCoresManagerList);
bctbx_list_free(tmpCoresManagerList);
LinphoneCoreCbs *cbs = linphone_factory_create_core_cbs(linphone_factory_get());
linphone_core_cbs_set_chat_room_exhumed(cbs, linphone_tester_chat_room_exhumed);
linphone_core_add_callbacks(pauline->lc, cbs);
linphone_core_manager_start(pauline, TRUE);
coresList = bctbx_list_append(coresList, pauline->lc);
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneChatRoomExhumed, 1,
liblinphone_tester_sip_timeout));
paulineOneToOneCr = linphone_core_get_chat_room(pauline->lc, exhumedConfAddr);
BC_ASSERT_EQUAL((int)linphone_chat_room_get_previouses_conference_ids_count(paulineOneToOneCr), 1, int,
"%d");
linphone_core_cbs_unref(cbs);
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneConferenceStateCreated, 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageReceived, 2,
liblinphone_tester_sip_timeout));
BC_ASSERT_FALSE(
wait_for_list(coresList, &pauline->stat.number_of_LinphoneConferenceStateTerminated, 1, 5000));
BC_ASSERT_EQUAL((int)linphone_chat_room_get_previouses_conference_ids_count(paulineOneToOneCr), 0, int,
6441644264436444644564466447644864496450645164526453645464556456645764586459646064616462646364646465646664676468646964706471647264736474647564766477647864796480648164826483648464856486648764886489649064916492649364946495649664976498649965006501650265036504650565066507650865096510
"%d");
} else {
// Pauline goes back online
ms_message("%s comes back online", linphone_core_get_identity(pauline->lc));
linphone_core_set_network_reachable(pauline->lc, TRUE);
BC_ASSERT_FALSE(
wait_for_list(coresList, &pauline->stat.number_of_LinphoneConferenceStateCreated, 2, 5000));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneChatRoomConferenceJoined, 2,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageReceived, 2,
liblinphone_tester_sip_timeout));
BC_ASSERT_FALSE(
wait_for_list(coresList, &pauline->stat.number_of_LinphoneConferenceStateTerminated, 1, 5000));
}
pauline2_messages = linphone_chat_room_get_history_size(pauline2OneToOneCr);
BC_ASSERT_EQUAL(pauline2_messages, 2, int, "%d");
pauline_messages = linphone_chat_room_get_history_size(paulineOneToOneCr);
BC_ASSERT_EQUAL(pauline_messages, 3, int, "%d");
marie_messages = linphone_chat_room_get_history_size(marieOneToOneCr);
BC_ASSERT_EQUAL(marie_messages, 1, int, "%d");
LinphoneChatMessage *post_exhume_message =
linphone_chat_room_create_message_from_utf8(marieOneToOneCr, "Sarah Connor ?");
linphone_chat_message_send(post_exhume_message);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneMessageSent, 3,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageReceived, 3,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline2->stat.number_of_LinphoneMessageReceived, 3,
liblinphone_tester_sip_timeout));
linphone_chat_message_unref(post_exhume_message);
pauline2_messages = linphone_chat_room_get_history_size(pauline2OneToOneCr);
BC_ASSERT_EQUAL(pauline2_messages, 3, int, "%d");
pauline_messages = linphone_chat_room_get_history_size(paulineOneToOneCr);
BC_ASSERT_EQUAL(pauline_messages, 4, int, "%d");
marie_messages = linphone_chat_room_get_history_size(marieOneToOneCr);
BC_ASSERT_EQUAL(marie_messages, 2, int, "%d");
}
linphone_config_set_int(linphone_core_get_config(pauline2->lc), "misc", "hide_empty_chat_rooms", 0);
linphone_config_set_int(linphone_core_get_config(pauline2->lc), "misc", "hide_chat_rooms_from_removed_proxies",
0);
const bctbx_list_t *pauline2_chat_rooms = linphone_core_get_chat_rooms(pauline2->lc);
BC_ASSERT_EQUAL((int)bctbx_list_size(pauline2_chat_rooms), 1, int, "%d");
linphone_config_set_int(linphone_core_get_config(pauline->lc), "misc", "hide_empty_chat_rooms", 0);
linphone_config_set_int(linphone_core_get_config(pauline->lc), "misc", "hide_chat_rooms_from_removed_proxies",
0);
const bctbx_list_t *pauline_chat_rooms = linphone_core_get_chat_rooms(pauline->lc);
BC_ASSERT_EQUAL((int)bctbx_list_size(pauline_chat_rooms), 1, int, "%d");
linphone_config_set_int(linphone_core_get_config(marie->lc), "misc", "hide_empty_chat_rooms", 0);
linphone_config_set_int(linphone_core_get_config(pauline->lc), "misc", "hide_chat_rooms_from_removed_proxies",
0);
const bctbx_list_t *marie_chat_rooms = linphone_core_get_chat_rooms(marie->lc);
BC_ASSERT_EQUAL((int)bctbx_list_size(marie_chat_rooms), 1, int, "%d");
BC_ASSERT_FALSE(linphone_chat_room_is_read_only(marieOneToOneCr));
BC_ASSERT_FALSE(linphone_chat_room_is_read_only(paulineOneToOneCr));
}
end:
if (confAddr) linphone_address_unref(confAddr);
if (exhumedConfAddr) linphone_address_unref(exhumedConfAddr);
6511651265136514651565166517651865196520652165226523652465256526652765286529653065316532653365346535653665376538653965406541654265436544654565466547654865496550655165526553655465556556655765586559656065616562656365646565656665676568656965706571657265736574657565766577657865796580
if (marieOneToOneCr) linphone_core_manager_delete_chat_room(marie, marieOneToOneCr, coresList);
if (paulineOneToOneCr) linphone_core_manager_delete_chat_room(pauline, paulineOneToOneCr, coresList);
if (conference_address_str) ms_free(conference_address_str);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
linphone_core_manager_destroy(pauline2);
}
static void exhume_one_to_one_chat_room_3(void) {
exhume_one_to_one_chat_room_3_base(FALSE);
}
static void exhume_one_to_one_chat_room_3_core_restart(void) {
exhume_one_to_one_chat_room_3_base(TRUE);
}
static void exhume_one_to_one_chat_room_4(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneChatRoom *marieOneToOneCr = NULL, *paulineOneToOneCr = NULL;
LinphoneAddress *confAddr = NULL, *exhumedConfAddr = NULL;
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
initialMarieStats = marie->stat;
initialPaulineStats = pauline->stat;
marieOneToOneCr = create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses,
"one to one", FALSE, LinphoneChatRoomEphemeralModeDeviceManaged);
if (!BC_ASSERT_PTR_NOT_NULL(marieOneToOneCr)) goto end;
confAddr = linphone_address_clone((LinphoneAddress *)linphone_chat_room_get_conference_address(marieOneToOneCr));
paulineOneToOneCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats, confAddr,
"one to one", 1, FALSE);
LinphoneChatMessage *message = linphone_chat_room_create_message_from_utf8(
paulineOneToOneCr,
"There is only one Lord of the Ring, only one who can bend it to his will. And he does not share power.");
linphone_chat_message_send(message);
BC_ASSERT_TRUE(
wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageSent, 1, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(
wait_for_list(coresList, &marie->stat.number_of_LinphoneMessageReceived, 1, liblinphone_tester_sip_timeout));
linphone_chat_message_unref(message);
BC_ASSERT_FALSE(linphone_chat_room_is_read_only(marieOneToOneCr));
BC_ASSERT_FALSE(linphone_chat_room_is_read_only(paulineOneToOneCr));
if (marieOneToOneCr) {
linphone_core_manager_delete_chat_room(marie, marieOneToOneCr, coresList);
BC_ASSERT_TRUE(wait_for_until(marie->lc, pauline->lc, &marie->stat.number_of_LinphoneConferenceStateTerminated,
1, liblinphone_tester_sip_timeout));
/* The chatroom from Pauline is expected to terminate as well */
BC_ASSERT_TRUE(wait_for_until(marie->lc, pauline->lc,
&pauline->stat.number_of_LinphoneConferenceStateTerminated, 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_FALSE(linphone_chat_room_is_read_only(paulineOneToOneCr));
bctbx_list_t *participants = linphone_chat_room_get_participants(paulineOneToOneCr);
6581658265836584658565866587658865896590659165926593659465956596659765986599660066016602660366046605660666076608660966106611661266136614661566166617661866196620662166226623662466256626662766286629663066316632663366346635663666376638663966406641664266436644664566466647664866496650
BC_ASSERT_EQUAL((int)bctbx_list_size(participants), 1, int, "%d");
bctbx_list_free_with_data(participants, (bctbx_list_free_func)linphone_participant_unref);
// Marie goes offline
int dummy = 0;
linphone_core_set_network_reachable(marie->lc, FALSE);
wait_for_list(coresList, &dummy, 1, 2000);
LinphoneChatMessage *exhume_message = linphone_chat_room_create_message_from_utf8(
paulineOneToOneCr, "I am Gandalf the White. And I come back to you now... at the turn of the tide.");
linphone_chat_message_send(exhume_message);
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneConferenceStateCreated, 2,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(
wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageSent, 2, liblinphone_tester_sip_timeout));
BC_ASSERT_FALSE(wait_for_list(coresList, &marie->stat.number_of_LinphoneConferenceStateCreated, 2,
liblinphone_tester_sip_timeout));
BC_ASSERT_FALSE(wait_for_list(coresList, &marie->stat.number_of_LinphoneMessageReceived, 2,
liblinphone_tester_sip_timeout));
linphone_chat_message_unref(exhume_message);
exhumedConfAddr =
linphone_address_ref((LinphoneAddress *)linphone_chat_room_get_conference_address(paulineOneToOneCr));
BC_ASSERT_PTR_NOT_NULL(exhumedConfAddr);
int pauline_messages = linphone_chat_room_get_history_size(paulineOneToOneCr);
BC_ASSERT_EQUAL(pauline_messages, 2, int, "%d");
// Marie goes back online
linphone_core_set_network_reachable(marie->lc, TRUE);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneConferenceStateCreated, 2,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneChatRoomConferenceJoined, 2,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneMessageReceived, 2,
liblinphone_tester_sip_timeout));
if (exhumedConfAddr) {
BC_ASSERT_FALSE(linphone_address_weak_equal(confAddr, exhumedConfAddr));
marieOneToOneCr = check_creation_chat_room_client_side(coresList, marie, &initialMarieStats,
exhumedConfAddr, "one to one", 1, FALSE);
BC_ASSERT_PTR_NOT_NULL(marieOneToOneCr);
if (marieOneToOneCr) {
int marie_messages = linphone_chat_room_get_history_size(marieOneToOneCr);
BC_ASSERT_EQUAL(marie_messages, 1, int, "%d");
LinphoneChatMessage *exhume_answer_message = linphone_chat_room_create_message_from_utf8(
marieOneToOneCr, "In my experience there is no such thing as luck.");
linphone_chat_message_send(exhume_answer_message);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneMessageSent, 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageReceived, 1,
liblinphone_tester_sip_timeout));
linphone_chat_message_unref(exhume_answer_message);
}
}
linphone_config_set_int(linphone_core_get_config(pauline->lc), "misc", "hide_empty_chat_rooms", 0);
linphone_config_set_int(linphone_core_get_config(pauline->lc), "misc", "hide_chat_rooms_from_removed_proxies",
0);
const bctbx_list_t *pauline_chat_rooms = linphone_core_get_chat_rooms(pauline->lc);
BC_ASSERT_EQUAL((int)bctbx_list_size(pauline_chat_rooms), 1, int, "%d");
linphone_config_set_int(linphone_core_get_config(marie->lc), "misc", "hide_empty_chat_rooms", 0);
linphone_config_set_int(linphone_core_get_config(pauline->lc), "misc", "hide_chat_rooms_from_removed_proxies",
0);
const bctbx_list_t *marie_chat_rooms = linphone_core_get_chat_rooms(marie->lc);
BC_ASSERT_EQUAL((int)bctbx_list_size(marie_chat_rooms), 1, int, "%d");
BC_ASSERT_FALSE(linphone_chat_room_is_read_only(marieOneToOneCr));
6651665266536654665566566657665866596660666166626663666466656666666766686669667066716672667366746675667666776678667966806681668266836684668566866687668866896690669166926693669466956696669766986699670067016702670367046705670667076708670967106711671267136714671567166717671867196720
BC_ASSERT_FALSE(linphone_chat_room_is_read_only(paulineOneToOneCr));
}
end:
if (confAddr) linphone_address_unref(confAddr);
if (exhumedConfAddr) linphone_address_unref(exhumedConfAddr);
if (marieOneToOneCr) linphone_core_manager_delete_chat_room(marie, marieOneToOneCr, coresList);
if (paulineOneToOneCr) linphone_core_manager_delete_chat_room(pauline, paulineOneToOneCr, coresList);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
}
static void group_chat_room_new_device_after_creation(void) {
LinphoneCoreManager *marie1 = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline1 = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *pauline2 = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *laure = linphone_core_manager_create("laure_tcp_rc");
LinphoneCoreManager *marie2 = NULL;
LinphoneChatRoom *marie1Cr = NULL, *marie2Cr = NULL, *pauline1Cr = NULL, *pauline2Cr = NULL, *laureCr = NULL;
const LinphoneAddress *confAddr = NULL;
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie1);
coresManagerList = bctbx_list_append(coresManagerList, pauline1);
coresManagerList = bctbx_list_append(coresManagerList, pauline2);
coresManagerList = bctbx_list_append(coresManagerList, laure);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline1->lc)));
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(laure->lc)));
stats initialMarie1Stats = marie1->stat;
stats initialPauline1Stats = pauline1->stat;
stats initialPauline2Stats = pauline2->stat;
stats initialLaureStats = laure->stat;
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
marie1Cr = create_chat_room_client_side(coresList, marie1, &initialMarie1Stats, participantsAddresses,
initialSubject, FALSE, LinphoneChatRoomEphemeralModeDeviceManaged);
if (!BC_ASSERT_PTR_NOT_NULL(marie1Cr)) goto end;
participantsAddresses = NULL;
confAddr = linphone_chat_room_get_conference_address(marie1Cr);
if (!BC_ASSERT_PTR_NOT_NULL(confAddr)) goto end;
// Check that the chat room is correctly created on Pauline1 and Pauline2's sides and that the participants are
// added
pauline1Cr = check_creation_chat_room_client_side(coresList, pauline1, &initialPauline1Stats, confAddr,
initialSubject, 2, FALSE);
pauline2Cr = check_creation_chat_room_client_side(coresList, pauline2, &initialPauline2Stats, confAddr,
initialSubject, 2, FALSE);
if (!(BC_ASSERT_PTR_NOT_NULL(pauline1Cr) && BC_ASSERT_PTR_NOT_NULL(pauline2Cr))) goto end;
// Check that the chat room is correctly created on Laure's side and that the participants are added
laureCr =
check_creation_chat_room_client_side(coresList, laure, &initialLaureStats, confAddr, initialSubject, 2, FALSE);
if (!BC_ASSERT_PTR_NOT_NULL(laureCr)) goto end;
// Marie adds a new device
marie2 = linphone_core_manager_create("marie_rc");
stats initialMarie2Stats = marie2->stat;
bctbx_list_t *tmpCoresManagerList = bctbx_list_append(NULL, marie2);
bctbx_list_t *tmpCoresList = init_core_for_conference(tmpCoresManagerList);
coresList = bctbx_list_concat(coresList, tmpCoresList);
start_core_for_conference(tmpCoresManagerList);
bctbx_list_free(tmpCoresManagerList);
6721672267236724672567266727672867296730673167326733673467356736673767386739674067416742674367446745674667476748674967506751675267536754675567566757675867596760676167626763676467656766676767686769677067716772677367746775677667776778677967806781678267836784678567866787678867896790
marie2Cr =
check_creation_chat_room_client_side(coresList, marie2, &initialMarie2Stats, confAddr, initialSubject, 2, TRUE);
if (!BC_ASSERT_PTR_NOT_NULL(marie2Cr)) goto end;
end:
// Clean db from chat room
if (marie1Cr) linphone_core_manager_delete_chat_room(marie1, marie1Cr, coresList);
if (marie2Cr) linphone_core_delete_chat_room(marie2->lc, marie2Cr);
if (pauline1Cr) linphone_core_manager_delete_chat_room(pauline1, pauline1Cr, coresList);
if (pauline2Cr) linphone_core_delete_chat_room(pauline2->lc, pauline2Cr);
if (laureCr) linphone_core_manager_delete_chat_room(laure, laureCr, coresList);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie1);
if (marie2) linphone_core_manager_destroy(marie2);
linphone_core_manager_destroy(pauline1);
linphone_core_manager_destroy(pauline2);
linphone_core_manager_destroy(laure);
}
static void group_chat_room_list_subscription(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *laure = linphone_core_manager_create("laure_tcp_rc");
LinphoneChatRoom *marieCr1 = NULL, *marieCr2 = NULL, *marieCr3 = NULL;
LinphoneChatRoom *paulineCr1 = NULL, *paulineCr2 = NULL, *paulineCr3 = NULL;
LinphoneChatRoom *laureCr1 = NULL, *laureCr2 = NULL, *laureCr3 = NULL;
const LinphoneAddress *confAddr1 = NULL, *confAddr2 = NULL, *confAddr3 = NULL;
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
coresManagerList = bctbx_list_append(coresManagerList, laure);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
stats initialLaureStats = laure->stat;
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(laure->lc)));
int dummy = 0;
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
marieCr1 = create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject,
FALSE, LinphoneChatRoomEphemeralModeDeviceManaged);
if (!BC_ASSERT_PTR_NOT_NULL(marieCr1)) goto end;
confAddr1 = linphone_chat_room_get_conference_address(marieCr1);
if (!BC_ASSERT_PTR_NOT_NULL(confAddr1)) goto end;
// Check that the chat room is correctly created on Pauline1 and Pauline2's sides and that the participants are
// added
paulineCr1 = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats, confAddr1,
initialSubject, 2, FALSE);
laureCr1 =
check_creation_chat_room_client_side(coresList, laure, &initialLaureStats, confAddr1, initialSubject, 2, FALSE);
if (!(BC_ASSERT_PTR_NOT_NULL(paulineCr1) && BC_ASSERT_PTR_NOT_NULL(laureCr1))) goto end;
initialMarieStats = marie->stat;
initialPaulineStats = pauline->stat;
initialLaureStats = laure->stat;
// Marie creates a new group chat room
initialSubject = "Friends";
participantsAddresses = NULL;
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
participantsAddresses =
6791679267936794679567966797679867996800680168026803680468056806680768086809681068116812681368146815681668176818681968206821682268236824682568266827682868296830683168326833683468356836683768386839684068416842684368446845684668476848684968506851685268536854685568566857685868596860
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(laure->lc)));
marieCr2 = create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject,
FALSE, LinphoneChatRoomEphemeralModeDeviceManaged);
if (!BC_ASSERT_PTR_NOT_NULL(marieCr2)) goto end;
confAddr2 = linphone_chat_room_get_conference_address(marieCr2);
if (!BC_ASSERT_PTR_NOT_NULL(confAddr2)) goto end;
// Check that the chat room is correctly created on Pauline1 and Pauline2's sides and that the participants are
// added
paulineCr2 = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats, confAddr2,
initialSubject, 2, FALSE);
laureCr2 =
check_creation_chat_room_client_side(coresList, laure, &initialLaureStats, confAddr2, initialSubject, 2, FALSE);
if (!(BC_ASSERT_PTR_NOT_NULL(paulineCr2) && BC_ASSERT_PTR_NOT_NULL(laureCr2))) goto end;
initialMarieStats = marie->stat;
initialPaulineStats = pauline->stat;
initialLaureStats = laure->stat;
// Marie creates a new group chat room
initialSubject = "Bros";
participantsAddresses = NULL;
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(laure->lc)));
marieCr3 = create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject,
FALSE, LinphoneChatRoomEphemeralModeDeviceManaged);
if (!BC_ASSERT_PTR_NOT_NULL(marieCr3)) goto end;
confAddr3 = linphone_chat_room_get_conference_address(marieCr3);
if (!BC_ASSERT_PTR_NOT_NULL(confAddr3)) goto end;
// Check that the chat room is correctly created on Pauline1 and Pauline2's sides and that the participants are
// added
paulineCr3 = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats, confAddr3,
initialSubject, 2, FALSE);
laureCr3 =
check_creation_chat_room_client_side(coresList, laure, &initialLaureStats, confAddr3, initialSubject, 2, FALSE);
if (!(BC_ASSERT_PTR_NOT_NULL(paulineCr3) && BC_ASSERT_PTR_NOT_NULL(laureCr3))) goto end;
participantsAddresses = NULL;
// Marie designates Pauline as admin in chat room 1
LinphoneAddress *paulineAddr = linphone_address_new(linphone_core_get_identity(pauline->lc));
LinphoneParticipant *paulineParticipant = linphone_chat_room_find_participant(marieCr1, paulineAddr);
linphone_address_unref(paulineAddr);
BC_ASSERT_PTR_NOT_NULL(paulineParticipant);
linphone_chat_room_set_participant_admin_status(marieCr1, paulineParticipant, TRUE);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_participant_admin_statuses_changed,
initialMarieStats.number_of_participant_admin_statuses_changed + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_participant_admin_statuses_changed,
initialPaulineStats.number_of_participant_admin_statuses_changed + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_participant_admin_statuses_changed,
initialLaureStats.number_of_participant_admin_statuses_changed + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(linphone_participant_is_admin(paulineParticipant));
// Pauline's device goes off
paulineAddr = linphone_address_clone(linphone_chat_room_get_local_address(paulineCr1));
coresList = bctbx_list_remove(coresList, pauline->lc);
linphone_core_set_network_reachable(pauline->lc, FALSE);
wait_for_list(coresList, &dummy, 1, 1000);
// Marie designates Laure as admin in chat rooms 1 & 3
LinphoneAddress *laureAddr = linphone_address_new(linphone_core_get_identity(laure->lc));
LinphoneParticipant *laureParticipant1 = linphone_chat_room_find_participant(marieCr1, laureAddr);
LinphoneParticipant *laureParticipant2 = linphone_chat_room_find_participant(marieCr2, laureAddr);
LinphoneParticipant *laureParticipant3 = linphone_chat_room_find_participant(marieCr3, laureAddr);
BC_ASSERT_PTR_NOT_NULL(laureParticipant1);
6861686268636864686568666867686868696870687168726873687468756876687768786879688068816882688368846885688668876888688968906891689268936894689568966897689868996900690169026903690469056906690769086909691069116912691369146915691669176918691969206921692269236924692569266927692869296930
BC_ASSERT_PTR_NOT_NULL(laureParticipant2);
BC_ASSERT_PTR_NOT_NULL(laureParticipant3);
linphone_chat_room_set_participant_admin_status(marieCr1, laureParticipant1, TRUE);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_participant_admin_statuses_changed,
initialMarieStats.number_of_participant_admin_statuses_changed + 2,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_participant_admin_statuses_changed,
initialLaureStats.number_of_participant_admin_statuses_changed + 2,
liblinphone_tester_sip_timeout));
BC_ASSERT_FALSE(wait_for_list(coresList, &pauline->stat.number_of_participant_admin_statuses_changed,
initialPaulineStats.number_of_participant_admin_statuses_changed + 2, 3000));
BC_ASSERT_TRUE(linphone_participant_is_admin(laureParticipant1));
linphone_chat_room_set_participant_admin_status(marieCr3, laureParticipant3, TRUE);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_participant_admin_statuses_changed,
initialMarieStats.number_of_participant_admin_statuses_changed + 3,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_participant_admin_statuses_changed,
initialLaureStats.number_of_participant_admin_statuses_changed + 3,
liblinphone_tester_sip_timeout));
BC_ASSERT_FALSE(wait_for_list(coresList, &pauline->stat.number_of_participant_admin_statuses_changed,
initialPaulineStats.number_of_participant_admin_statuses_changed + 3, 3000));
BC_ASSERT_TRUE(linphone_participant_is_admin(laureParticipant3));
// Marie now changes the subject or chat room 1
const char *newSubject = "New subject";
linphone_chat_room_set_subject(marieCr1, newSubject);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_subject_changed,
initialMarieStats.number_of_subject_changed + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_subject_changed,
initialLaureStats.number_of_subject_changed + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_FALSE(wait_for_list(coresList, &pauline->stat.number_of_subject_changed,
initialPaulineStats.number_of_subject_changed + 1, 3000));
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(marieCr1), newSubject);
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(laureCr1), newSubject);
// Pauline is back
linphone_core_manager_reinit(pauline);
bctbx_list_t *tmpCoresManagerList = bctbx_list_append(NULL, pauline);
bctbx_list_t *tmpCoresList = init_core_for_conference(tmpCoresManagerList);
bctbx_list_free(tmpCoresManagerList);
coresList = bctbx_list_concat(coresList, tmpCoresList);
linphone_core_manager_start(pauline, TRUE);
paulineCr1 = linphone_core_find_chat_room(pauline->lc, confAddr1, paulineAddr);
paulineCr2 = linphone_core_find_chat_room(pauline->lc, confAddr2, paulineAddr);
paulineCr3 = linphone_core_find_chat_room(pauline->lc, confAddr3, paulineAddr);
BC_ASSERT_PTR_NOT_NULL(paulineCr1);
BC_ASSERT_PTR_NOT_NULL(paulineCr2);
BC_ASSERT_PTR_NOT_NULL(paulineCr3);
linphone_address_unref(paulineAddr);
LinphoneParticipant *laureParticipantOfPauline1 = linphone_chat_room_find_participant(paulineCr1, laureAddr);
LinphoneParticipant *laureParticipantOfPauline2 = linphone_chat_room_find_participant(paulineCr2, laureAddr);
LinphoneParticipant *laureParticipantOfPauline3 = linphone_chat_room_find_participant(paulineCr3, laureAddr);
BC_ASSERT_PTR_NOT_NULL(laureParticipantOfPauline1);
BC_ASSERT_PTR_NOT_NULL(laureParticipantOfPauline2);
BC_ASSERT_PTR_NOT_NULL(laureParticipantOfPauline3);
linphone_address_unref(laureAddr);
wait_for_list(coresList, &dummy, 1, 5000);
// Check that Pauline receive the missing info and not more
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_participant_admin_statuses_changed,
initialPaulineStats.number_of_participant_admin_statuses_changed + 2,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(linphone_participant_is_admin(laureParticipantOfPauline1));
BC_ASSERT_TRUE(linphone_participant_is_admin(laureParticipantOfPauline3));
BC_ASSERT_FALSE(linphone_participant_is_admin(laureParticipantOfPauline2));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_subject_changed,
initialPaulineStats.number_of_subject_changed + 1, 10000));
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(paulineCr1), newSubject);
// Check that Pauline can still receive info once back
6931693269336934693569366937693869396940694169426943694469456946694769486949695069516952695369546955695669576958695969606961696269636964696569666967696869696970697169726973697469756976697769786979698069816982698369846985698669876988698969906991699269936994699569966997699869997000
// Marie now changes the subject or chat room 1
newSubject = "New New subject";
linphone_chat_room_set_subject(marieCr1, newSubject);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_subject_changed,
initialMarieStats.number_of_subject_changed + 2, 10000));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_subject_changed,
initialLaureStats.number_of_subject_changed + 2, 10000));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_subject_changed,
initialPaulineStats.number_of_subject_changed + 2, 10000));
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(marieCr1), newSubject);
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(laureCr1), newSubject);
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(paulineCr1), newSubject);
// Marie now changes the subject or chat room 2
newSubject = "Newer subject";
linphone_chat_room_set_subject(marieCr2, newSubject);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_subject_changed,
initialMarieStats.number_of_subject_changed + 3, 10000));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_subject_changed,
initialLaureStats.number_of_subject_changed + 3, 10000));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_subject_changed,
initialPaulineStats.number_of_subject_changed + 3, 10000));
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(marieCr2), newSubject);
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(laureCr2), newSubject);
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(paulineCr2), newSubject);
// Marie now changes the subject or chat room 3
newSubject = "Newest subject";
linphone_chat_room_set_subject(marieCr3, newSubject);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_subject_changed,
initialMarieStats.number_of_subject_changed + 4, 10000));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_subject_changed,
initialLaureStats.number_of_subject_changed + 4, 10000));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_subject_changed,
initialPaulineStats.number_of_subject_changed + 4, 10000));
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(marieCr3), newSubject);
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(laureCr3), newSubject);
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(paulineCr3), newSubject);
end:
// Clean db from chat room
if (marieCr1) linphone_core_manager_delete_chat_room(marie, marieCr1, coresList);
if (paulineCr1) linphone_core_manager_delete_chat_room(pauline, paulineCr1, coresList);
if (laureCr1) linphone_core_manager_delete_chat_room(laure, laureCr1, coresList);
if (marieCr2) linphone_core_manager_delete_chat_room(marie, marieCr2, coresList);
if (paulineCr2) linphone_core_manager_delete_chat_room(pauline, paulineCr2, coresList);
if (laureCr2) linphone_core_manager_delete_chat_room(laure, laureCr2, coresList);
if (marieCr3) linphone_core_manager_delete_chat_room(marie, marieCr3, coresList);
if (paulineCr3) linphone_core_manager_delete_chat_room(pauline, paulineCr3, coresList);
if (laureCr3) linphone_core_manager_delete_chat_room(laure, laureCr3, coresList);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
linphone_core_manager_destroy(laure);
}
static void group_chat_room_complex_participant_removal_scenario(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *laure = linphone_core_manager_create("laure_tcp_rc");
LinphoneChatRoom *marieCr = NULL, *paulineCr = NULL, *newLaureCr = NULL;
const LinphoneAddress *confAddr = NULL;
LinphoneAddress *laureDeviceAddress;
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
coresManagerList = bctbx_list_append(coresManagerList, laure);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
7001700270037004700570067007700870097010701170127013701470157016701770187019702070217022702370247025702670277028702970307031703270337034703570367037703870397040704170427043704470457046704770487049705070517052705370547055705670577058705970607061706270637064706570667067706870697070
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(laure->lc)));
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
stats initialLaureStats = laure->stat;
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
marieCr = create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject,
FALSE, LinphoneChatRoomEphemeralModeDeviceManaged);
if (!BC_ASSERT_PTR_NOT_NULL(marieCr)) goto end;
participantsAddresses = NULL;
confAddr = linphone_chat_room_get_conference_address(marieCr);
if (!BC_ASSERT_PTR_NOT_NULL(confAddr)) goto end;
// Check that the chat room is correctly created on Pauline's side and that the participants are added
paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats, confAddr, initialSubject,
2, FALSE);
if (!BC_ASSERT_PTR_NOT_NULL(paulineCr)) goto end;
// Check that the chat room is correctly created on Laure's side and that the participants are added
check_creation_chat_room_client_side(coresList, laure, &initialLaureStats, confAddr, initialSubject, 2, FALSE);
// Restart Laure core
linphone_core_set_network_reachable(laure->lc, FALSE);
LinphoneAddress *laureAddr = linphone_address_clone(laure->identity);
coresList = bctbx_list_remove(coresList, laure->lc);
linphone_core_manager_reinit(laure);
bctbx_list_t *tmpCoresManagerList = bctbx_list_append(NULL, laure);
bctbx_list_t *tmpCoresList = init_core_for_conference(tmpCoresManagerList);
bctbx_list_free(tmpCoresManagerList);
coresList = bctbx_list_concat(coresList, tmpCoresList);
linphone_core_manager_start(laure, TRUE);
initialLaureStats = laure->stat;
// Marie removes Laure from the chat room
LinphoneParticipant *laureParticipant = linphone_chat_room_find_participant(marieCr, laureAddr);
BC_ASSERT_PTR_NOT_NULL(laureParticipant);
linphone_chat_room_remove_participant(marieCr, laureParticipant);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_participants_removed,
initialMarieStats.number_of_participants_removed + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_participants_removed,
initialPaulineStats.number_of_participants_removed + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_LinphoneConferenceStateTerminated,
initialLaureStats.number_of_LinphoneConferenceStateTerminated + 1,
liblinphone_tester_sip_timeout));
wait_for_list(coresList, 0, 1, 2000);
initialLaureStats = laure->stat;
linphone_proxy_config_refresh_register(linphone_core_get_default_proxy_config(laure->lc));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_LinphoneRegistrationOk,
initialLaureStats.number_of_LinphoneRegistrationOk + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_FALSE(wait_for_list(coresList, &laure->stat.number_of_LinphoneConferenceStateTerminated,
initialLaureStats.number_of_LinphoneConferenceStateTerminated + 1, 3000));
// Marie adds Laure to the chat room
participantsAddresses = bctbx_list_append(participantsAddresses, laureAddr);
linphone_chat_room_add_participants(marieCr, participantsAddresses);
bctbx_list_free_with_data(participantsAddresses, (bctbx_list_free_func)linphone_address_unref);
participantsAddresses = NULL;
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_participants_added,
initialMarieStats.number_of_participants_added + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_participants_added,
initialPaulineStats.number_of_participants_added + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_LinphoneConferenceStateCreationPending,
7071707270737074707570767077707870797080708170827083708470857086708770887089709070917092709370947095709670977098709971007101710271037104710571067107710871097110711171127113711471157116711771187119712071217122712371247125712671277128712971307131713271337134713571367137713871397140
initialLaureStats.number_of_LinphoneConferenceStateCreationPending + 1, 10000));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_LinphoneConferenceStateCreated,
initialLaureStats.number_of_LinphoneConferenceStateCreated + 1, 10000));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_LinphoneChatRoomConferenceJoined,
initialLaureStats.number_of_LinphoneChatRoomConferenceJoined + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(marieCr), 2, int, "%d");
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(paulineCr), 2, int, "%d");
char *laureIdentity = linphone_core_get_device_identity(laure->lc);
laureDeviceAddress = linphone_address_new(laureIdentity);
bctbx_free(laureIdentity);
newLaureCr = linphone_core_find_chat_room(laure->lc, confAddr, laureDeviceAddress);
if (!BC_ASSERT_PTR_NOT_NULL(newLaureCr)) goto end;
linphone_address_unref(laureDeviceAddress);
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(newLaureCr), 2, int, "%d");
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(newLaureCr), initialSubject);
BC_ASSERT_FALSE(linphone_chat_room_has_been_left(newLaureCr));
unsigned int nbLaureConferenceCreatedEventsBeforeRestart = 0;
bctbx_list_t *laureHistory = linphone_chat_room_get_history_events(newLaureCr, 0);
for (bctbx_list_t *item = laureHistory; item; item = bctbx_list_next(item)) {
LinphoneEventLog *event = (LinphoneEventLog *)bctbx_list_get_data(item);
if (linphone_event_log_get_type(event) == LinphoneEventLogTypeConferenceCreated)
nbLaureConferenceCreatedEventsBeforeRestart++;
}
bctbx_list_free_with_data(laureHistory, (bctbx_list_free_func)linphone_event_log_unref);
BC_ASSERT_EQUAL(nbLaureConferenceCreatedEventsBeforeRestart, 2, unsigned int, "%u");
initialLaureStats = laure->stat;
linphone_proxy_config_refresh_register(linphone_core_get_default_proxy_config(laure->lc));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_LinphoneRegistrationOk,
initialLaureStats.number_of_LinphoneRegistrationOk + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_FALSE(wait_for_list(coresList, &laure->stat.number_of_LinphoneChatRoomConferenceJoined,
initialLaureStats.number_of_LinphoneChatRoomConferenceJoined + 1, 3000));
BC_ASSERT_FALSE(wait_for_list(coresList, &laure->stat.number_of_LinphoneConferenceStateTerminated,
initialLaureStats.number_of_LinphoneConferenceStateTerminated + 1, 3000));
unsigned int nbLaureConferenceCreatedEventsAfterRestart = 0;
laureHistory = linphone_chat_room_get_history_events(newLaureCr, 0);
for (bctbx_list_t *item = laureHistory; item; item = bctbx_list_next(item)) {
LinphoneEventLog *event = (LinphoneEventLog *)bctbx_list_get_data(item);
if (linphone_event_log_get_type(event) == LinphoneEventLogTypeConferenceCreated)
nbLaureConferenceCreatedEventsAfterRestart++;
}
bctbx_list_free_with_data(laureHistory, (bctbx_list_free_func)linphone_event_log_unref);
BC_ASSERT_EQUAL(nbLaureConferenceCreatedEventsAfterRestart, nbLaureConferenceCreatedEventsBeforeRestart,
unsigned int, "%u");
end:
// Clean db from chat room
if (marieCr) linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
if (newLaureCr) linphone_core_manager_delete_chat_room(laure, newLaureCr, coresList);
if (paulineCr) linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
linphone_core_manager_destroy(laure);
}
static void group_chat_room_subscription_denied(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *laure = linphone_core_manager_create("laure_tcp_rc");
LinphoneChatRoom *marieCr = NULL, *paulineCr = NULL, *laureCr = NULL;
const LinphoneAddress *confAddr = NULL;
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
7141714271437144714571467147714871497150715171527153715471557156715771587159716071617162716371647165716671677168716971707171717271737174717571767177717871797180718171827183718471857186718771887189719071917192719371947195719671977198719972007201720272037204720572067207720872097210
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
coresManagerList = bctbx_list_append(coresManagerList, laure);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
LinphoneAddress *paulineAddress = linphone_address_new(linphone_core_get_identity(pauline->lc));
start_core_for_conference(coresManagerList);
participantsAddresses = bctbx_list_append(participantsAddresses, linphone_address_ref(paulineAddress));
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(laure->lc)));
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
stats initialLaureStats = laure->stat;
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
marieCr = create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject,
FALSE, LinphoneChatRoomEphemeralModeDeviceManaged);
if (!BC_ASSERT_PTR_NOT_NULL(marieCr)) goto end;
confAddr = linphone_chat_room_get_conference_address(marieCr);
if (!BC_ASSERT_PTR_NOT_NULL(confAddr)) goto end;
// Check that the chat room is correctly created on Laure's side and that the participants are added
paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats, confAddr, initialSubject,
2, FALSE);
if (!BC_ASSERT_PTR_NOT_NULL(paulineCr)) goto end;
// Check that the chat room is correctly created on Laure's side and that the participants are added
laureCr =
check_creation_chat_room_client_side(coresList, laure, &initialLaureStats, confAddr, initialSubject, 2, FALSE);
if (!BC_ASSERT_PTR_NOT_NULL(laureCr)) goto end;
// Simulate pauline has disconnected
linphone_core_set_network_reachable(pauline->lc, FALSE);
LinphoneParticipant *paulineParticipant = linphone_chat_room_find_participant(marieCr, paulineAddress);
BC_ASSERT_PTR_NOT_NULL(paulineParticipant);
linphone_chat_room_remove_participant(marieCr, paulineParticipant);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_participants_removed,
initialMarieStats.number_of_participants_removed + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_participants_removed,
initialLaureStats.number_of_participants_removed + 1, liblinphone_tester_sip_timeout));
// Reconnect pauline
linphone_core_set_network_reachable(pauline->lc, TRUE);
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneConferenceStateTerminated,
initialPaulineStats.number_of_LinphoneConferenceStateTerminated + 1,
liblinphone_tester_sip_timeout));
end:
// Clean db from chat room
if (marieCr) linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
if (laureCr) linphone_core_manager_delete_chat_room(laure, laureCr, coresList);
if (paulineCr) linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
linphone_address_unref(paulineAddress);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
linphone_core_manager_destroy(laure);
}
static void search_friend_chat_room_participants(void) {
LinphoneMagicSearch *magicSearch = NULL;
bctbx_list_t *resultList = NULL;
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
7211721272137214721572167217721872197220722172227223722472257226722772287229723072317232723372347235723672377238723972407241724272437244724572467247724872497250725172527253725472557256725772587259726072617262726372647265726672677268726972707271727272737274727572767277727872797280
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *laure = linphone_core_manager_create("laure_tcp_rc");
LinphoneCoreManager *chloe = linphone_core_manager_create("chloe_rc");
LinphoneChatRoom *marieCr = NULL, *paulineCr = NULL, *laureCr = NULL;
const LinphoneAddress *confAddr = NULL;
LinphoneProxyConfig *laurePC = linphone_core_get_default_proxy_config(laure->lc);
LinphoneProxyConfig *mariePC = linphone_core_get_default_proxy_config(marie->lc);
const LinphoneAddress *laureIdentity = linphone_proxy_config_get_identity_address(laurePC);
const LinphoneAddress *marieIdentity = linphone_proxy_config_get_identity_address(mariePC);
char *laureI = linphone_address_as_string_uri_only(laureIdentity);
char *marieI = linphone_address_as_string_uri_only(marieIdentity);
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
coresManagerList = bctbx_list_append(coresManagerList, laure);
coresManagerList = bctbx_list_append(coresManagerList, chloe);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(laure->lc)));
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
stats initialLaureStats = laure->stat;
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
marieCr = create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject,
FALSE, LinphoneChatRoomEphemeralModeDeviceManaged);
if (!BC_ASSERT_PTR_NOT_NULL(marieCr)) goto end;
confAddr = linphone_chat_room_get_conference_address(marieCr);
if (!BC_ASSERT_PTR_NOT_NULL(confAddr)) goto end;
// Check that the chat room is correctly created on Pauline's side and that the participants are added
paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats, confAddr, initialSubject,
2, FALSE);
if (!BC_ASSERT_PTR_NOT_NULL(paulineCr)) goto end;
// Check that the chat room is correctly created on Laure's side and that the participants are added
laureCr =
check_creation_chat_room_client_side(coresList, laure, &initialLaureStats, confAddr, initialSubject, 2, FALSE);
if (!BC_ASSERT_PTR_NOT_NULL(laureCr)) goto end;
magicSearch = linphone_magic_search_new(pauline->lc);
resultList = linphone_magic_search_get_contact_list_from_filter(magicSearch, "", "");
if (BC_ASSERT_PTR_NOT_NULL(resultList)) {
BC_ASSERT_EQUAL((int)bctbx_list_size(resultList), 2, int, "%d");
_check_friend_result_list_2(pauline->lc, resultList, 0, laureI, NULL, LinphoneMagicSearchSourceChatRooms);
_check_friend_result_list_2(pauline->lc, resultList, 1, marieI, NULL, LinphoneMagicSearchSourceChatRooms);
bctbx_list_free_with_data(resultList, (bctbx_list_free_func)linphone_magic_search_unref);
}
ms_free(laureI);
ms_free(marieI);
linphone_magic_search_reset_search_cache(magicSearch);
linphone_magic_search_unref(magicSearch);
end:
// Clean db from chat room
if (marieCr) linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
if (laureCr) linphone_core_manager_delete_chat_room(laure, laureCr, coresList);
if (paulineCr) linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
7281728272837284728572867287728872897290729172927293729472957296729772987299730073017302730373047305730673077308730973107311731273137314731573167317731873197320732173227323732473257326732773287329733073317332733373347335733673377338733973407341734273437344734573467347734873497350
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
linphone_core_manager_destroy(laure);
linphone_core_manager_destroy(chloe);
}
static void group_chat_room_participant_devices_name(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *pauline2 = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *laure = linphone_core_manager_create("laure_tcp_rc");
LinphoneCoreManager *chloe = linphone_core_manager_create("chloe_rc");
LinphoneCoreManager *chloe2 = linphone_core_manager_create("chloe_rc");
LinphoneCoreManager *chloe3 = linphone_core_manager_create("chloe_rc");
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
coresManagerList = bctbx_list_append(coresManagerList, pauline2);
coresManagerList = bctbx_list_append(coresManagerList, laure);
coresManagerList = bctbx_list_append(coresManagerList, chloe);
coresManagerList = bctbx_list_append(coresManagerList, chloe2);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
linphone_core_set_user_agent(marie->lc, "blabla (Marie device) blibli/blublu (bloblo)", NULL);
linphone_core_set_user_agent(pauline->lc, "blabla (Pauline device 1) blibli/blublu (bloblo)", NULL);
linphone_core_set_user_agent(pauline2->lc, "blabla (Pauline device 2) blibli/blublu (bloblo)", NULL);
linphone_core_set_user_agent(laure->lc, "(Laure device ((toto) tata) (titi)) (bloblo)", NULL);
linphone_core_set_user_agent(chloe->lc, "blabla (Chloe device 1) blibli/blublu (bloblo)", NULL);
linphone_core_set_user_agent(chloe2->lc, "blabla (Chloe device 2) blibli/blublu (bloblo)", NULL);
start_core_for_conference(coresManagerList);
LinphoneAddress *marieAddress = linphone_address_new(linphone_core_get_identity(marie->lc));
LinphoneAddress *paulineAddress =
linphone_address_ref(linphone_address_new(linphone_core_get_identity(pauline->lc)));
LinphoneAddress *laureAddress = linphone_address_ref(linphone_address_new(linphone_core_get_identity(laure->lc)));
LinphoneAddress *chloeAddress = linphone_address_new(linphone_core_get_identity(chloe->lc));
LinphoneAddress *marieDeviceAddress =
linphone_address_clone(linphone_proxy_config_get_contact(linphone_core_get_default_proxy_config(marie->lc)));
LinphoneAddress *paulineDeviceAddress1 =
linphone_address_clone(linphone_proxy_config_get_contact(linphone_core_get_default_proxy_config(pauline->lc)));
LinphoneAddress *paulineDeviceAddress2 =
linphone_address_clone(linphone_proxy_config_get_contact(linphone_core_get_default_proxy_config(pauline2->lc)));
LinphoneAddress *laureDeviceAddress =
linphone_address_clone(linphone_proxy_config_get_contact(linphone_core_get_default_proxy_config(laure->lc)));
LinphoneAddress *chloeDeviceAddress1 =
linphone_address_clone(linphone_proxy_config_get_contact(linphone_core_get_default_proxy_config(chloe->lc)));
LinphoneAddress *chloeDeviceAddress2 =
linphone_address_clone(linphone_proxy_config_get_contact(linphone_core_get_default_proxy_config(chloe2->lc)));
participantsAddresses = bctbx_list_append(participantsAddresses, paulineAddress);
participantsAddresses = bctbx_list_append(participantsAddresses, laureAddress);
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
stats initialPaulineStats2 = pauline2->stat;
stats initialLaureStats = laure->stat;
stats initialChloeStats = chloe->stat;
stats initialChloeStats2 = chloe2->stat;
stats initialChloeStats3 = chloe3->stat;
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
LinphoneChatRoom *marieCr =
create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject, FALSE,
LinphoneChatRoomEphemeralModeDeviceManaged);
LinphoneAddress *confAddr = linphone_address_clone(linphone_chat_room_get_conference_address(marieCr));
// Check that the chat room is correctly created on Pauline's side and that the participants are added
LinphoneChatRoom *paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats,
confAddr, initialSubject, 2, FALSE);
// Check that the chat room is correctly created on Pauline's side and that the participants are added
7351735273537354735573567357735873597360736173627363736473657366736773687369737073717372737373747375737673777378737973807381738273837384738573867387738873897390739173927393739473957396739773987399740074017402740374047405740674077408740974107411741274137414741574167417741874197420
LinphoneChatRoom *paulineCr2 = check_creation_chat_room_client_side(coresList, pauline2, &initialPaulineStats2,
confAddr, initialSubject, 2, FALSE);
// Check that the chat room is correctly created on Laure's side and that the participants are added
LinphoneChatRoom *laureCr =
check_creation_chat_room_client_side(coresList, laure, &initialLaureStats, confAddr, initialSubject, 2, FALSE);
// Check device's name in Marie's chat room
LinphoneParticipant *marieParticipant = linphone_chat_room_get_me(marieCr);
LinphoneParticipant *paulineParticipant = linphone_chat_room_find_participant(marieCr, paulineAddress);
LinphoneParticipant *laureParticipant = linphone_chat_room_find_participant(marieCr, laureAddress);
LinphoneParticipantDevice *marieDevice = linphone_participant_find_device(marieParticipant, marieDeviceAddress);
LinphoneParticipantDevice *paulineDevice =
linphone_participant_find_device(paulineParticipant, paulineDeviceAddress1);
LinphoneParticipantDevice *paulineDevice2 =
linphone_participant_find_device(paulineParticipant, paulineDeviceAddress2);
LinphoneParticipantDevice *laureDevice = linphone_participant_find_device(laureParticipant, laureDeviceAddress);
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(marieDevice), "Marie device");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(paulineDevice), "Pauline device 1");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(paulineDevice2), "Pauline device 2");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(laureDevice), "Laure device ((toto) tata) (titi)");
// Check device's name in Pauline1's chat room
marieParticipant = linphone_chat_room_find_participant(paulineCr, marieAddress);
paulineParticipant = linphone_chat_room_get_me(paulineCr);
laureParticipant = linphone_chat_room_find_participant(marieCr, laureAddress);
marieDevice = linphone_participant_find_device(marieParticipant, marieDeviceAddress);
paulineDevice = linphone_participant_find_device(paulineParticipant, paulineDeviceAddress1);
paulineDevice2 = linphone_participant_find_device(paulineParticipant, paulineDeviceAddress2);
laureDevice = linphone_participant_find_device(laureParticipant, laureDeviceAddress);
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(marieDevice), "Marie device");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(paulineDevice), "Pauline device 1");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(paulineDevice2), "Pauline device 2");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(laureDevice), "Laure device ((toto) tata) (titi)");
// Check device's name in Pauline2's chat room
marieParticipant = linphone_chat_room_find_participant(paulineCr2, marieAddress);
paulineParticipant = linphone_chat_room_get_me(paulineCr2);
laureParticipant = linphone_chat_room_find_participant(paulineCr2, laureAddress);
marieDevice = linphone_participant_find_device(marieParticipant, marieDeviceAddress);
paulineDevice = linphone_participant_find_device(paulineParticipant, paulineDeviceAddress1);
paulineDevice2 = linphone_participant_find_device(paulineParticipant, paulineDeviceAddress2);
laureDevice = linphone_participant_find_device(laureParticipant, laureDeviceAddress);
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(marieDevice), "Marie device");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(paulineDevice), "Pauline device 1");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(paulineDevice2), "Pauline device 2");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(laureDevice), "Laure device ((toto) tata) (titi)");
// Check device's name in Laure's chat room
marieParticipant = linphone_chat_room_find_participant(laureCr, marieAddress);
paulineParticipant = linphone_chat_room_find_participant(laureCr, paulineAddress);
laureParticipant = linphone_chat_room_get_me(laureCr);
marieDevice = linphone_participant_find_device(marieParticipant, marieDeviceAddress);
paulineDevice = linphone_participant_find_device(paulineParticipant, paulineDeviceAddress1);
paulineDevice2 = linphone_participant_find_device(paulineParticipant, paulineDeviceAddress2);
laureDevice = linphone_participant_find_device(laureParticipant, laureDeviceAddress);
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(marieDevice), "Marie device");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(paulineDevice), "Pauline device 1");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(paulineDevice2), "Pauline device 2");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(laureDevice), "Laure device ((toto) tata) (titi)");
// Reset stats
marie->stat = initialMarieStats;
pauline->stat = initialPaulineStats;
pauline2->stat = initialPaulineStats2;
laure->stat = initialLaureStats;
chloe->stat = initialChloeStats;
chloe2->stat = initialChloeStats2;
chloe3->stat = initialChloeStats3;
7421742274237424742574267427742874297430743174327433743474357436743774387439744074417442744374447445744674477448744974507451745274537454745574567457745874597460746174627463746474657466746774687469747074717472747374747475747674777478747974807481748274837484748574867487748874897490
// Marie adds Chloe to the chat room
participantsAddresses = NULL;
participantsAddresses = bctbx_list_append(participantsAddresses, chloeAddress);
linphone_chat_room_add_participants(marieCr, participantsAddresses);
// Check that the chat room is correctly created on Chloe's side and that she was added everywhere
LinphoneChatRoom *chloeCr =
check_creation_chat_room_client_side(coresList, chloe, &initialChloeStats, confAddr, initialSubject, 3, 0);
LinphoneChatRoom *chloeCr2 =
check_creation_chat_room_client_side(coresList, chloe2, &initialChloeStats2, confAddr, initialSubject, 3, 0);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_participants_added,
initialMarieStats.number_of_participants_added + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_participant_devices_added,
initialMarieStats.number_of_participant_devices_added + 2,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_participants_added,
initialPaulineStats.number_of_participants_added + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_participant_devices_added,
initialPaulineStats.number_of_participant_devices_added + 2,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline2->stat.number_of_participants_added,
initialPaulineStats2.number_of_participants_added + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline2->stat.number_of_participant_devices_added,
initialPaulineStats2.number_of_participant_devices_added + 2,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_participants_added,
initialLaureStats.number_of_participants_added + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_participant_devices_added,
initialLaureStats.number_of_participant_devices_added + 2,
liblinphone_tester_sip_timeout));
// Check device's name in Chloe's chat room
LinphoneParticipant *chloeParticipant = linphone_chat_room_get_me(chloeCr);
marieParticipant = linphone_chat_room_find_participant(chloeCr, marieAddress);
paulineParticipant = linphone_chat_room_find_participant(chloeCr, paulineAddress);
laureParticipant = linphone_chat_room_find_participant(chloeCr, laureAddress);
marieDevice = linphone_participant_find_device(marieParticipant, marieDeviceAddress);
paulineDevice = linphone_participant_find_device(paulineParticipant, paulineDeviceAddress1);
paulineDevice2 = linphone_participant_find_device(paulineParticipant, paulineDeviceAddress2);
laureDevice = linphone_participant_find_device(laureParticipant, laureDeviceAddress);
LinphoneParticipantDevice *chloeDevice = linphone_participant_find_device(chloeParticipant, chloeDeviceAddress1);
LinphoneParticipantDevice *chloeDevice2 = linphone_participant_find_device(chloeParticipant, chloeDeviceAddress2);
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(marieDevice), "Marie device");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(paulineDevice), "Pauline device 1");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(paulineDevice2), "Pauline device 2");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(laureDevice), "Laure device ((toto) tata) (titi)");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(chloeDevice), "Chloe device 1");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(chloeDevice2), "Chloe device 2");
// Check device's name in Chloe2's chat room
chloeParticipant = linphone_chat_room_get_me(chloeCr2);
marieParticipant = linphone_chat_room_find_participant(chloeCr2, marieAddress);
paulineParticipant = linphone_chat_room_find_participant(chloeCr2, paulineAddress);
laureParticipant = linphone_chat_room_find_participant(chloeCr2, laureAddress);
marieDevice = linphone_participant_find_device(marieParticipant, marieDeviceAddress);
paulineDevice = linphone_participant_find_device(paulineParticipant, paulineDeviceAddress1);
paulineDevice2 = linphone_participant_find_device(paulineParticipant, paulineDeviceAddress2);
laureDevice = linphone_participant_find_device(laureParticipant, laureDeviceAddress);
chloeDevice = linphone_participant_find_device(chloeParticipant, chloeDeviceAddress1);
chloeDevice2 = linphone_participant_find_device(chloeParticipant, chloeDeviceAddress2);
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(marieDevice), "Marie device");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(paulineDevice), "Pauline device 1");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(paulineDevice2), "Pauline device 2");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(laureDevice), "Laure device ((toto) tata) (titi)");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(chloeDevice), "Chloe device 1");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(chloeDevice2), "Chloe device 2");
// Check Chloe's devices name in other chat rooms
// Marie
7491749274937494749574967497749874997500750175027503750475057506750775087509751075117512751375147515751675177518751975207521752275237524752575267527752875297530753175327533753475357536753775387539754075417542754375447545754675477548754975507551755275537554755575567557755875597560
chloeParticipant = linphone_chat_room_find_participant(marieCr, chloeAddress);
chloeDevice = linphone_participant_find_device(chloeParticipant, chloeDeviceAddress1);
chloeDevice2 = linphone_participant_find_device(chloeParticipant, chloeDeviceAddress2);
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(chloeDevice), "Chloe device 1");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(chloeDevice2), "Chloe device 2");
// Pauline
chloeParticipant = linphone_chat_room_find_participant(paulineCr, chloeAddress);
chloeDevice = linphone_participant_find_device(chloeParticipant, chloeDeviceAddress1);
chloeDevice2 = linphone_participant_find_device(chloeParticipant, chloeDeviceAddress2);
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(chloeDevice), "Chloe device 1");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(chloeDevice2), "Chloe device 2");
// Pauline 2
chloeParticipant = linphone_chat_room_find_participant(paulineCr2, chloeAddress);
chloeDevice = linphone_participant_find_device(chloeParticipant, chloeDeviceAddress1);
chloeDevice2 = linphone_participant_find_device(chloeParticipant, chloeDeviceAddress2);
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(chloeDevice), "Chloe device 1");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(chloeDevice2), "Chloe device 2");
// Laure
chloeParticipant = linphone_chat_room_find_participant(laureCr, chloeAddress);
chloeDevice = linphone_participant_find_device(chloeParticipant, chloeDeviceAddress1);
chloeDevice2 = linphone_participant_find_device(chloeParticipant, chloeDeviceAddress2);
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(chloeDevice), "Chloe device 1");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(chloeDevice2), "Chloe device 2");
// Reset stats
marie->stat = initialMarieStats;
pauline->stat = initialPaulineStats;
pauline2->stat = initialPaulineStats2;
laure->stat = initialLaureStats;
chloe->stat = initialChloeStats;
chloe2->stat = initialChloeStats2;
chloe3->stat = initialChloeStats3;
// Chloe adds a new device
coresManagerList = NULL;
coresManagerList = bctbx_list_append(coresManagerList, chloe3);
init_core_for_conference(coresManagerList);
coresList = bctbx_list_append(coresList, chloe3->lc);
linphone_core_set_user_agent(chloe3->lc, "blabla (Chloe device 3) blibli/blublu (bloblo)", NULL);
start_core_for_conference(coresManagerList);
LinphoneAddress *chloeDeviceAddress3 =
linphone_address_clone(linphone_proxy_config_get_contact(linphone_core_get_default_proxy_config(chloe3->lc)));
LinphoneChatRoom *chloeCr3 =
check_creation_chat_room_client_side(coresList, chloe3, &initialChloeStats3, confAddr, initialSubject, 3, 0);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_participant_devices_added,
initialMarieStats.number_of_participant_devices_added + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_participant_devices_added,
initialPaulineStats.number_of_participant_devices_added + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline2->stat.number_of_participant_devices_added,
initialPaulineStats2.number_of_participant_devices_added + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_participant_devices_added,
initialLaureStats.number_of_participant_devices_added + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &chloe->stat.number_of_participant_devices_added,
initialChloeStats.number_of_participant_devices_added + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &chloe2->stat.number_of_participant_devices_added,
initialChloeStats2.number_of_participant_devices_added + 1,
liblinphone_tester_sip_timeout));
// Check device's name in Chloe3's chat room
chloeParticipant = linphone_chat_room_get_me(chloeCr3);
marieParticipant = linphone_chat_room_find_participant(chloeCr3, marieAddress);
paulineParticipant = linphone_chat_room_find_participant(chloeCr3, paulineAddress);
7561756275637564756575667567756875697570757175727573757475757576757775787579758075817582758375847585758675877588758975907591759275937594759575967597759875997600760176027603760476057606760776087609761076117612761376147615761676177618761976207621762276237624762576267627762876297630
laureParticipant = linphone_chat_room_find_participant(chloeCr3, laureAddress);
marieDevice = linphone_participant_find_device(marieParticipant, marieDeviceAddress);
paulineDevice = linphone_participant_find_device(paulineParticipant, paulineDeviceAddress1);
paulineDevice2 = linphone_participant_find_device(paulineParticipant, paulineDeviceAddress2);
laureDevice = linphone_participant_find_device(laureParticipant, laureDeviceAddress);
chloeDevice = linphone_participant_find_device(chloeParticipant, chloeDeviceAddress1);
chloeDevice2 = linphone_participant_find_device(chloeParticipant, chloeDeviceAddress2);
LinphoneParticipantDevice *chloeDevice3 = linphone_participant_find_device(chloeParticipant, chloeDeviceAddress3);
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(marieDevice), "Marie device");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(paulineDevice), "Pauline device 1");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(paulineDevice2), "Pauline device 2");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(laureDevice), "Laure device ((toto) tata) (titi)");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(chloeDevice), "Chloe device 1");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(chloeDevice2), "Chloe device 2");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(chloeDevice3), "Chloe device 3");
// Check Chloe3's device name in other chat rooms
// Marie
chloeParticipant = linphone_chat_room_find_participant(marieCr, chloeAddress);
chloeDevice3 = linphone_participant_find_device(chloeParticipant, chloeDeviceAddress3);
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(chloeDevice3), "Chloe device 3");
// Pauline
chloeParticipant = linphone_chat_room_find_participant(paulineCr, chloeAddress);
chloeDevice3 = linphone_participant_find_device(chloeParticipant, chloeDeviceAddress3);
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(chloeDevice3), "Chloe device 3");
// Pauline 2
chloeParticipant = linphone_chat_room_find_participant(paulineCr2, chloeAddress);
chloeDevice3 = linphone_participant_find_device(chloeParticipant, chloeDeviceAddress3);
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(chloeDevice3), "Chloe device 3");
// Laure
chloeParticipant = linphone_chat_room_find_participant(laureCr, chloeAddress);
chloeDevice3 = linphone_participant_find_device(chloeParticipant, chloeDeviceAddress3);
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(chloeDevice3), "Chloe device 3");
// Chloe
chloeParticipant = linphone_chat_room_get_me(chloeCr);
chloeDevice3 = linphone_participant_find_device(chloeParticipant, chloeDeviceAddress3);
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(chloeDevice3), "Chloe device 3");
// Chloe2
chloeParticipant = linphone_chat_room_get_me(chloeCr2);
chloeDevice3 = linphone_participant_find_device(chloeParticipant, chloeDeviceAddress3);
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(chloeDevice3), "Chloe device 3");
// Still works after restart
linphone_core_manager_restart(marie, TRUE);
linphone_core_manager_restart(pauline, TRUE);
linphone_core_manager_restart(pauline2, TRUE);
linphone_core_manager_restart(laure, TRUE);
linphone_core_manager_restart(chloe, TRUE);
linphone_core_manager_restart(chloe2, TRUE);
linphone_core_manager_restart(chloe3, TRUE);
coresList = NULL;
coresList = bctbx_list_append(coresList, marie->lc);
coresList = bctbx_list_append(coresList, pauline->lc);
coresList = bctbx_list_append(coresList, pauline2->lc);
coresList = bctbx_list_append(coresList, laure->lc);
coresList = bctbx_list_append(coresList, chloe->lc);
coresList = bctbx_list_append(coresList, chloe2->lc);
coresList = bctbx_list_append(coresList, chloe3->lc);
// Marie
marieCr = linphone_core_find_chat_room(marie->lc, confAddr, marieDeviceAddress);
LinphoneChatRoomCbs *cbs = linphone_factory_create_chat_room_cbs(linphone_factory_get());
linphone_chat_room_cbs_set_state_changed(cbs, chat_room_state_changed);
linphone_chat_room_add_callbacks(marieCr, cbs);
linphone_chat_room_cbs_unref(cbs);
7631763276337634763576367637763876397640764176427643764476457646764776487649765076517652765376547655765676577658765976607661766276637664766576667667766876697670767176727673767476757676767776787679768076817682768376847685768676877688768976907691769276937694769576967697769876997700
BC_ASSERT_PTR_NOT_NULL(marieCr);
marieParticipant = linphone_chat_room_get_me(marieCr);
paulineParticipant = linphone_chat_room_find_participant(marieCr, paulineAddress);
laureParticipant = linphone_chat_room_find_participant(marieCr, laureAddress);
chloeParticipant = linphone_chat_room_find_participant(marieCr, chloeAddress);
marieDevice = linphone_participant_find_device(marieParticipant, marieDeviceAddress);
paulineDevice = linphone_participant_find_device(paulineParticipant, paulineDeviceAddress1);
paulineDevice2 = linphone_participant_find_device(paulineParticipant, paulineDeviceAddress2);
laureDevice = linphone_participant_find_device(laureParticipant, laureDeviceAddress);
chloeDevice = linphone_participant_find_device(chloeParticipant, chloeDeviceAddress1);
chloeDevice2 = linphone_participant_find_device(chloeParticipant, chloeDeviceAddress2);
chloeDevice3 = linphone_participant_find_device(chloeParticipant, chloeDeviceAddress3);
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(marieDevice), "Marie device");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(paulineDevice), "Pauline device 1");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(paulineDevice2), "Pauline device 2");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(laureDevice), "Laure device ((toto) tata) (titi)");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(chloeDevice), "Chloe device 1");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(chloeDevice2), "Chloe device 2");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(chloeDevice3), "Chloe device 3");
// Pauline1
paulineCr = linphone_core_find_chat_room(pauline->lc, confAddr, paulineDeviceAddress1);
cbs = linphone_factory_create_chat_room_cbs(linphone_factory_get());
linphone_chat_room_cbs_set_state_changed(cbs, chat_room_state_changed);
linphone_chat_room_add_callbacks(paulineCr, cbs);
linphone_chat_room_cbs_unref(cbs);
BC_ASSERT_PTR_NOT_NULL(paulineCr);
marieParticipant = linphone_chat_room_find_participant(paulineCr, marieAddress);
paulineParticipant = linphone_chat_room_get_me(paulineCr);
laureParticipant = linphone_chat_room_find_participant(paulineCr, laureAddress);
chloeParticipant = linphone_chat_room_find_participant(paulineCr, chloeAddress);
marieDevice = linphone_participant_find_device(marieParticipant, marieDeviceAddress);
paulineDevice = linphone_participant_find_device(paulineParticipant, paulineDeviceAddress1);
paulineDevice2 = linphone_participant_find_device(paulineParticipant, paulineDeviceAddress2);
laureDevice = linphone_participant_find_device(laureParticipant, laureDeviceAddress);
chloeDevice = linphone_participant_find_device(chloeParticipant, chloeDeviceAddress1);
chloeDevice2 = linphone_participant_find_device(chloeParticipant, chloeDeviceAddress2);
chloeDevice3 = linphone_participant_find_device(chloeParticipant, chloeDeviceAddress3);
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(marieDevice), "Marie device");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(paulineDevice), "Pauline device 1");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(paulineDevice2), "Pauline device 2");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(laureDevice), "Laure device ((toto) tata) (titi)");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(chloeDevice), "Chloe device 1");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(chloeDevice2), "Chloe device 2");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(chloeDevice3), "Chloe device 3");
// Pauline2
paulineCr2 = linphone_core_find_chat_room(pauline2->lc, confAddr, paulineDeviceAddress2);
cbs = linphone_factory_create_chat_room_cbs(linphone_factory_get());
linphone_chat_room_cbs_set_state_changed(cbs, chat_room_state_changed);
linphone_chat_room_add_callbacks(paulineCr2, cbs);
linphone_chat_room_cbs_unref(cbs);
BC_ASSERT_PTR_NOT_NULL(paulineCr2);
marieParticipant = linphone_chat_room_find_participant(paulineCr2, marieAddress);
paulineParticipant = linphone_chat_room_get_me(paulineCr2);
laureParticipant = linphone_chat_room_find_participant(paulineCr2, laureAddress);
chloeParticipant = linphone_chat_room_find_participant(paulineCr2, chloeAddress);
marieDevice = linphone_participant_find_device(marieParticipant, marieDeviceAddress);
paulineDevice = linphone_participant_find_device(paulineParticipant, paulineDeviceAddress1);
paulineDevice2 = linphone_participant_find_device(paulineParticipant, paulineDeviceAddress2);
laureDevice = linphone_participant_find_device(laureParticipant, laureDeviceAddress);
chloeDevice = linphone_participant_find_device(chloeParticipant, chloeDeviceAddress1);
chloeDevice2 = linphone_participant_find_device(chloeParticipant, chloeDeviceAddress2);
chloeDevice3 = linphone_participant_find_device(chloeParticipant, chloeDeviceAddress3);
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(marieDevice), "Marie device");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(paulineDevice), "Pauline device 1");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(paulineDevice2), "Pauline device 2");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(laureDevice), "Laure device ((toto) tata) (titi)");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(chloeDevice), "Chloe device 1");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(chloeDevice2), "Chloe device 2");
7701770277037704770577067707770877097710771177127713771477157716771777187719772077217722772377247725772677277728772977307731773277337734773577367737773877397740774177427743774477457746774777487749775077517752775377547755775677577758775977607761776277637764776577667767776877697770
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(chloeDevice3), "Chloe device 3");
// Laure
laureCr = linphone_core_find_chat_room(laure->lc, confAddr, laureDeviceAddress);
cbs = linphone_factory_create_chat_room_cbs(linphone_factory_get());
linphone_chat_room_cbs_set_state_changed(cbs, chat_room_state_changed);
linphone_chat_room_add_callbacks(laureCr, cbs);
linphone_chat_room_cbs_unref(cbs);
BC_ASSERT_PTR_NOT_NULL(laureCr);
marieParticipant = linphone_chat_room_find_participant(laureCr, marieAddress);
paulineParticipant = linphone_chat_room_find_participant(laureCr, paulineAddress);
laureParticipant = linphone_chat_room_get_me(laureCr);
chloeParticipant = linphone_chat_room_find_participant(laureCr, chloeAddress);
marieDevice = linphone_participant_find_device(marieParticipant, marieDeviceAddress);
paulineDevice = linphone_participant_find_device(paulineParticipant, paulineDeviceAddress1);
paulineDevice2 = linphone_participant_find_device(paulineParticipant, paulineDeviceAddress2);
laureDevice = linphone_participant_find_device(laureParticipant, laureDeviceAddress);
chloeDevice = linphone_participant_find_device(chloeParticipant, chloeDeviceAddress1);
chloeDevice2 = linphone_participant_find_device(chloeParticipant, chloeDeviceAddress2);
chloeDevice3 = linphone_participant_find_device(chloeParticipant, chloeDeviceAddress3);
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(marieDevice), "Marie device");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(paulineDevice), "Pauline device 1");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(paulineDevice2), "Pauline device 2");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(laureDevice), "Laure device ((toto) tata) (titi)");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(chloeDevice), "Chloe device 1");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(chloeDevice2), "Chloe device 2");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(chloeDevice3), "Chloe device 3");
// Chloe1
chloeCr = linphone_core_find_chat_room(chloe->lc, confAddr, chloeDeviceAddress1);
cbs = linphone_factory_create_chat_room_cbs(linphone_factory_get());
linphone_chat_room_cbs_set_state_changed(cbs, chat_room_state_changed);
linphone_chat_room_add_callbacks(chloeCr, cbs);
linphone_chat_room_cbs_unref(cbs);
BC_ASSERT_PTR_NOT_NULL(chloeCr);
marieParticipant = linphone_chat_room_find_participant(chloeCr, marieAddress);
paulineParticipant = linphone_chat_room_find_participant(chloeCr, paulineAddress);
laureParticipant = linphone_chat_room_find_participant(chloeCr, laureAddress);
chloeParticipant = linphone_chat_room_get_me(chloeCr);
marieDevice = linphone_participant_find_device(marieParticipant, marieDeviceAddress);
paulineDevice = linphone_participant_find_device(paulineParticipant, paulineDeviceAddress1);
paulineDevice2 = linphone_participant_find_device(paulineParticipant, paulineDeviceAddress2);
laureDevice = linphone_participant_find_device(laureParticipant, laureDeviceAddress);
chloeDevice = linphone_participant_find_device(chloeParticipant, chloeDeviceAddress1);
chloeDevice2 = linphone_participant_find_device(chloeParticipant, chloeDeviceAddress2);
chloeDevice3 = linphone_participant_find_device(chloeParticipant, chloeDeviceAddress3);
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(marieDevice), "Marie device");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(paulineDevice), "Pauline device 1");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(paulineDevice2), "Pauline device 2");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(laureDevice), "Laure device ((toto) tata) (titi)");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(chloeDevice), "Chloe device 1");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(chloeDevice2), "Chloe device 2");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(chloeDevice3), "Chloe device 3");
// Chloe2
chloeCr2 = linphone_core_find_chat_room(chloe2->lc, confAddr, chloeDeviceAddress2);
cbs = linphone_factory_create_chat_room_cbs(linphone_factory_get());
linphone_chat_room_cbs_set_state_changed(cbs, chat_room_state_changed);
linphone_chat_room_add_callbacks(chloeCr2, cbs);
linphone_chat_room_cbs_unref(cbs);
BC_ASSERT_PTR_NOT_NULL(chloeCr2);
marieParticipant = linphone_chat_room_find_participant(chloeCr2, marieAddress);
paulineParticipant = linphone_chat_room_find_participant(chloeCr2, paulineAddress);
laureParticipant = linphone_chat_room_find_participant(chloeCr2, laureAddress);
chloeParticipant = linphone_chat_room_get_me(chloeCr2);
marieDevice = linphone_participant_find_device(marieParticipant, marieDeviceAddress);
paulineDevice = linphone_participant_find_device(paulineParticipant, paulineDeviceAddress1);
paulineDevice2 = linphone_participant_find_device(paulineParticipant, paulineDeviceAddress2);
laureDevice = linphone_participant_find_device(laureParticipant, laureDeviceAddress);
chloeDevice = linphone_participant_find_device(chloeParticipant, chloeDeviceAddress1);
7771777277737774777577767777777877797780778177827783778477857786778777887789779077917792779377947795779677977798779978007801780278037804780578067807780878097810781178127813781478157816781778187819782078217822782378247825782678277828782978307831783278337834783578367837783878397840
chloeDevice2 = linphone_participant_find_device(chloeParticipant, chloeDeviceAddress2);
chloeDevice3 = linphone_participant_find_device(chloeParticipant, chloeDeviceAddress3);
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(marieDevice), "Marie device");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(paulineDevice), "Pauline device 1");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(paulineDevice2), "Pauline device 2");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(laureDevice), "Laure device ((toto) tata) (titi)");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(chloeDevice), "Chloe device 1");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(chloeDevice2), "Chloe device 2");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(chloeDevice3), "Chloe device 3");
// Chloe3
chloeCr3 = linphone_core_find_chat_room(chloe3->lc, confAddr, chloeDeviceAddress3);
cbs = linphone_factory_create_chat_room_cbs(linphone_factory_get());
linphone_chat_room_cbs_set_state_changed(cbs, chat_room_state_changed);
linphone_chat_room_add_callbacks(chloeCr3, cbs);
linphone_chat_room_cbs_unref(cbs);
BC_ASSERT_PTR_NOT_NULL(chloeCr3);
marieParticipant = linphone_chat_room_find_participant(chloeCr3, marieAddress);
paulineParticipant = linphone_chat_room_find_participant(chloeCr3, paulineAddress);
laureParticipant = linphone_chat_room_find_participant(chloeCr3, laureAddress);
chloeParticipant = linphone_chat_room_get_me(chloeCr3);
marieDevice = linphone_participant_find_device(marieParticipant, marieDeviceAddress);
paulineDevice = linphone_participant_find_device(paulineParticipant, paulineDeviceAddress1);
paulineDevice2 = linphone_participant_find_device(paulineParticipant, paulineDeviceAddress2);
laureDevice = linphone_participant_find_device(laureParticipant, laureDeviceAddress);
chloeDevice = linphone_participant_find_device(chloeParticipant, chloeDeviceAddress1);
chloeDevice2 = linphone_participant_find_device(chloeParticipant, chloeDeviceAddress2);
chloeDevice3 = linphone_participant_find_device(chloeParticipant, chloeDeviceAddress3);
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(marieDevice), "Marie device");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(paulineDevice), "Pauline device 1");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(paulineDevice2), "Pauline device 2");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(laureDevice), "Laure device ((toto) tata) (titi)");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(chloeDevice), "Chloe device 1");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(chloeDevice2), "Chloe device 2");
BC_ASSERT_STRING_EQUAL(linphone_participant_device_get_name(chloeDevice3), "Chloe device 3");
linphone_address_unref(marieAddress);
linphone_address_unref(paulineAddress);
linphone_address_unref(laureAddress);
linphone_address_unref(chloeAddress);
linphone_address_unref(confAddr);
linphone_address_unref(marieDeviceAddress);
linphone_address_unref(paulineDeviceAddress1);
linphone_address_unref(paulineDeviceAddress2);
linphone_address_unref(laureDeviceAddress);
linphone_address_unref(chloeDeviceAddress1);
linphone_address_unref(chloeDeviceAddress2);
linphone_address_unref(chloeDeviceAddress3);
// Clean db from chat room
linphone_core_manager_delete_chat_room(laure, laureCr, coresList);
linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
linphone_core_manager_delete_chat_room(pauline2, paulineCr2, coresList);
linphone_core_manager_delete_chat_room(chloe, chloeCr, coresList);
linphone_core_manager_delete_chat_room(chloe2, chloeCr2, coresList);
linphone_core_manager_delete_chat_room(chloe3, chloeCr3, coresList);
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
linphone_core_manager_destroy(pauline2);
linphone_core_manager_destroy(laure);
linphone_core_manager_destroy(chloe);
linphone_core_manager_destroy(chloe2);
linphone_core_manager_destroy(chloe3);
}
static void add_device_one_to_one_chat_room_other_left(void) {
7841784278437844784578467847784878497850785178527853785478557856785778587859786078617862786378647865786678677868786978707871787278737874787578767877787878797880788178827883788478857886788778887889789078917892789378947895789678977898789979007901790279037904790579067907790879097910
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *pauline2 = linphone_core_manager_create("pauline_rc");
LinphoneAddress *confAddr = NULL;
LinphoneChatRoom *paulineCr = NULL, *paulineCr2 = NULL, *marieCr = NULL;
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
coresManagerList = bctbx_list_append(coresManagerList, pauline2);
bctbx_list_t *coresList = init_core_for_conference_with_groupchat_version(coresManagerList, "1.0");
linphone_core_manager_start(marie, TRUE);
linphone_core_manager_start(pauline, TRUE);
LinphoneAddress *paulineAddress = linphone_address_new(linphone_core_get_identity(pauline->lc));
participantsAddresses = bctbx_list_append(participantsAddresses, paulineAddress);
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
stats initialPaulineStats2 = pauline2->stat;
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
marieCr = create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject,
FALSE, LinphoneChatRoomEphemeralModeDeviceManaged);
if (!BC_ASSERT_PTR_NOT_NULL(marieCr)) goto clean;
confAddr = (LinphoneAddress *)linphone_chat_room_get_conference_address(marieCr);
if (!BC_ASSERT_PTR_NOT_NULL(confAddr)) goto clean;
confAddr = linphone_address_clone(confAddr);
// Check that the chat room is correctly created on Pauline's side and that the participants are added
paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats, confAddr, initialSubject,
1, FALSE);
if (!BC_ASSERT_PTR_NOT_NULL(paulineCr)) goto clean;
// Marie leaves the chat room
linphone_chat_room_leave(marieCr);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneConferenceStateTerminationPending,
initialMarieStats.number_of_LinphoneConferenceStateTerminationPending + 1, 100));
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneConferenceStateTerminated,
initialMarieStats.number_of_LinphoneConferenceStateTerminated + 1,
liblinphone_tester_sip_timeout));
int pauline_number_of_participant_devices_added = pauline->stat.number_of_participant_devices_added;
linphone_core_manager_start(pauline2, TRUE);
// Check that the chat room is correctly created on Pauline's side and that the participants are added
paulineCr2 = check_creation_chat_room_client_side(coresList, pauline2, &initialPaulineStats2, confAddr,
initialSubject, 1, FALSE);
if (!BC_ASSERT_PTR_NOT_NULL(paulineCr2)) goto clean;
// Also, pauline should receive a notification that pauline2 device was added.
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_participant_devices_added,
pauline_number_of_participant_devices_added + 1, liblinphone_tester_sip_timeout));
wait_for_list(coresList, NULL, 0, 1000);
clean:
// Clean db from chat room
if (pauline && paulineCr) linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
if (pauline2 && paulineCr) linphone_core_manager_delete_chat_room(pauline2, paulineCr2, coresList);
if (marie && marieCr) linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
if (confAddr) linphone_address_unref(confAddr);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
linphone_core_manager_destroy(pauline2);
}
7911791279137914791579167917791879197920792179227923792479257926792779287929793079317932793379347935793679377938793979407941794279437944794579467947794879497950795179527953795479557956795779587959796079617962796379647965796679677968796979707971797279737974797579767977797879797980
/*
* This test simulates a case where whatever the reason the server thinks a client device is part of a given chatroom,
*but the client device has no longer this information.
**/
static void group_chat_loss_of_client_context(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *laure = linphone_core_manager_create("laure_tcp_rc");
LinphoneChatRoom *marieCr = NULL, *paulineCr = NULL;
const LinphoneAddress *confAddr = NULL;
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
coresManagerList = bctbx_list_append(coresManagerList, laure);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(laure->lc)));
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
stats initialLaureStats = laure->stat;
// Save Laure's db before it becomes part of a group chat.
const char *uri = linphone_config_get_string(linphone_core_get_config(laure->lc), "storage", "uri", "");
char *uriCopy = bc_tester_file("linphone_tester.db");
BC_ASSERT_FALSE(liblinphone_tester_copy_file(uri, uriCopy));
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
marieCr = create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject,
FALSE, LinphoneChatRoomEphemeralModeDeviceManaged);
if (!BC_ASSERT_PTR_NOT_NULL(marieCr)) goto end;
confAddr = linphone_chat_room_get_conference_address(marieCr);
if (!BC_ASSERT_PTR_NOT_NULL(confAddr)) goto end;
// Check that the chat room is correctly created on Pauline's side and that the participants are added
paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats, confAddr, initialSubject,
2, FALSE);
if (!BC_ASSERT_PTR_NOT_NULL(paulineCr)) goto end;
// Check that the chat room is correctly created on Laure's side and that the participants are added
check_creation_chat_room_client_side(coresList, laure, &initialLaureStats, confAddr, initialSubject, 2, FALSE);
// Save Laure's db now that it is part of the group chat
uri = linphone_config_get_string(linphone_core_get_config(laure->lc), "storage", "uri", "");
char *uriCopyAfter = bc_tester_file("linphone_tester2.db");
BC_ASSERT_FALSE(liblinphone_tester_copy_file(uri, uriCopyAfter));
// Restore old db to Laure and restart it.
laure->database_path = uriCopy;
coresList = bctbx_list_remove(coresList, laure->lc);
linphone_core_manager_reinit(laure);
bctbx_list_t *tmpCoresManagerList = bctbx_list_append(NULL, laure);
bctbx_list_t *tmpCoresList = init_core_for_conference(tmpCoresManagerList);
bctbx_list_free(tmpCoresManagerList);
coresList = bctbx_list_concat(coresList, tmpCoresList);
linphone_core_manager_start(laure, TRUE);
// Pauline sends a message, laure shall not receive it, in any way.
if (paulineCr) {
_send_message(paulineCr, "Salut");
}
wait_for_list(coresList, NULL, 0, 2000);
BC_ASSERT_TRUE(linphone_core_get_chat_rooms(laure->lc) == NULL);
7981798279837984798579867987798879897990799179927993799479957996799779987999800080018002800380048005800680078008800980108011801280138014801580168017801880198020802180228023802480258026802780288029803080318032803380348035803680378038803980408041804280438044804580468047804880498050
// Now restarts Laure with good db in order to clean the chatroom properly.
// Restore old db to Laure and restart it.
laure->database_path = uriCopyAfter;
coresList = bctbx_list_remove(coresList, laure->lc);
linphone_core_manager_reinit(laure);
tmpCoresManagerList = bctbx_list_append(NULL, laure);
tmpCoresList = init_core_for_conference(tmpCoresManagerList);
bctbx_list_free(tmpCoresManagerList);
coresList = bctbx_list_concat(coresList, tmpCoresList);
linphone_core_manager_start(laure, TRUE);
// Clean chatroom from databases.
if (BC_ASSERT_TRUE(linphone_core_get_chat_rooms(laure->lc) != NULL)) {
LinphoneChatRoom *laureCr = (LinphoneChatRoom *)linphone_core_get_chat_rooms(laure->lc)->data;
linphone_core_manager_delete_chat_room(laure, laureCr, coresList);
}
end:
if (marieCr) linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
if (paulineCr) linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
linphone_core_manager_destroy(laure);
}
static void participant_removed_then_added(void) {
LinphoneCoreManager *marie1 = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline1 = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *laure = linphone_core_manager_create("laure_tcp_rc");
LinphoneChatRoom *marie1Cr = NULL, *pauline1Cr = NULL, *newPauline1Cr = NULL, *laureCr = NULL;
const LinphoneAddress *confAddr = NULL;
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie1);
coresManagerList = bctbx_list_append(coresManagerList, pauline1);
coresManagerList = bctbx_list_append(coresManagerList, laure);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline1->lc)));
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(laure->lc)));
stats initialMarie1Stats = marie1->stat;
stats initialPauline1Stats = pauline1->stat;
stats initialLaureStats = laure->stat;
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
marie1Cr = create_chat_room_client_side(coresList, marie1, &initialMarie1Stats, participantsAddresses,
initialSubject, FALSE, LinphoneChatRoomEphemeralModeDeviceManaged);
if (!BC_ASSERT_PTR_NOT_NULL(marie1Cr)) goto end;
participantsAddresses = NULL;
confAddr = linphone_chat_room_get_conference_address(marie1Cr);
if (!BC_ASSERT_PTR_NOT_NULL(confAddr)) goto end;
// Check that the chat room is correctly created on Pauline1
pauline1Cr = check_creation_chat_room_client_side(coresList, pauline1, &initialPauline1Stats, confAddr,
initialSubject, 2, FALSE);
if (!BC_ASSERT_PTR_NOT_NULL(pauline1Cr)) goto end;
// Check that the chat room is correctly created on Laure's side and that the participants are added
laureCr =
check_creation_chat_room_client_side(coresList, laure, &initialLaureStats, confAddr, initialSubject, 2, FALSE);
if (!BC_ASSERT_PTR_NOT_NULL(laureCr)) goto end;
// Pauline restart to make use of list subscription ::this part (core restart) is leaking memory
8051805280538054805580568057805880598060806180628063806480658066806780688069807080718072807380748075807680778078807980808081808280838084808580868087808880898090809180928093809480958096809780988099810081018102810381048105810681078108810981108111811281138114811581168117811881198120
coresList = bctbx_list_remove(coresList, pauline1->lc);
linphone_core_manager_reinit(pauline1);
bctbx_list_t *tmpCoresManagerList = bctbx_list_append(NULL, pauline1);
bctbx_list_t *tmpCoresList = init_core_for_conference(tmpCoresManagerList);
bctbx_list_free(tmpCoresManagerList);
coresList = bctbx_list_concat(coresList, tmpCoresList);
linphone_core_manager_start(pauline1, TRUE);
// Check that the chat room has correctly created on Pauline's side and that the participants are added
pauline1Cr =
check_has_chat_room_client_side(coresList, pauline1, &initialPauline1Stats, confAddr, initialSubject, 2, FALSE);
// wait for first notify to be received by pauline
wait_for_list(coresList, NULL, 0, 1000);
// Pauline leaving but keeping a ref like a Java GC can do, this is the key part of this test.
linphone_chat_room_ref(pauline1Cr);
linphone_core_delete_chat_room(pauline1->lc, pauline1Cr);
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline1->stat.number_of_LinphoneConferenceStateDeleted,
initialPauline1Stats.number_of_LinphoneConferenceStateDeleted + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &marie1->stat.number_of_participants_removed,
initialMarie1Stats.number_of_participants_removed + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_participants_removed,
initialLaureStats.number_of_participants_removed + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(marie1Cr), 1, int, "%d");
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(laureCr), 1, int, "%d");
size_t paulineCrNo = bctbx_list_size(linphone_core_get_chat_rooms(pauline1->lc));
BC_ASSERT_EQUAL(paulineCrNo, 0, size_t, "%0zu");
// Send a message when Pauline is left to test ordering between events and messages.
wait_for_list(coresList, NULL, 0, 1500); // Wait enough time to make a difference on time_t
const char *textMessage = "Hello";
LinphoneChatMessage *message = _send_message(marie1Cr, textMessage);
wait_for_list(coresList, NULL, 0, 1500); // Wait enough time to make a difference on time_t
linphone_chat_message_unref(message);
// Marie1 adds Pauline back to the chat room
initialMarie1Stats = marie1->stat;
initialLaureStats = laure->stat;
initialPauline1Stats = pauline1->stat;
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline1->lc)));
linphone_chat_room_add_participants(marie1Cr, participantsAddresses);
// BC_ASSERT_TRUE(wait_for_list(coresList, &marie1->stat.number_of_participants_added,
// initialMarie1Stats.number_of_participants_added + 1, liblinphone_tester_sip_timeout));
// BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_participants_added,
// initialLaureStats.number_of_participants_added + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_chat_room_participants(coresList, marie1Cr, 2, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_chat_room_participants(coresList, laureCr, 2, liblinphone_tester_sip_timeout));
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(marie1Cr), 2, int, "%d");
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(laureCr), 2, int, "%d");
newPauline1Cr = check_creation_chat_room_client_side(coresList, pauline1, &initialPauline1Stats, confAddr,
initialSubject, 2, FALSE);
if (!BC_ASSERT_PTR_NOT_NULL(newPauline1Cr)) goto end;
BC_ASSERT_EQUAL(linphone_chat_room_get_nb_participants(newPauline1Cr), 2, int, "%d");
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(newPauline1Cr), initialSubject);
// Check timestamps ordering in history
bctbx_list_t *history = linphone_chat_room_get_history_events(marie1Cr, 3); // Leave + Message + Join
bctbx_list_t *itHistory = history;
int step = 0;
time_t lastTime = 0;
while (itHistory) {
LinphoneEventLog *event = (LinphoneEventLog *)bctbx_list_get_data(itHistory);
switch (step) {
8121812281238124812581268127812881298130813181328133813481358136813781388139814081418142814381448145814681478148814981508151815281538154815581568157815881598160816181628163816481658166816781688169817081718172817381748175817681778178817981808181818281838184818581868187818881898190
case 0:
BC_ASSERT_EQUAL((int)linphone_event_log_get_type(event),
LinphoneEventLogTypeConferenceParticipantRemoved, int, "%d");
lastTime = linphone_event_log_get_creation_time(event); // Main ordering (Leave + Message + Join)
break;
case 1: {
BC_ASSERT_EQUAL((int)linphone_event_log_get_type(event), LinphoneEventLogTypeConferenceChatMessage, int,
"%d");
LinphoneChatMessage *message = linphone_event_log_get_chat_message(event);
time_t messageTime = linphone_chat_message_get_time(message);
BC_ASSERT_TRUE(lastTime < messageTime); // Main ordering (Leave + Message + Join)
BC_ASSERT_TRUE(messageTime >= linphone_event_log_get_creation_time(
event)); // A send message timestamp should be after its creation.
lastTime = messageTime;
} break;
case 2:
BC_ASSERT_EQUAL((int)linphone_event_log_get_type(event), LinphoneEventLogTypeConferenceParticipantAdded,
int, "%d");
BC_ASSERT_TRUE(lastTime <
linphone_event_log_get_creation_time(event)); // Main ordering (Leave + Message + Join)
lastTime = linphone_event_log_get_creation_time(event);
break;
default: {
}
}
++step;
itHistory = bctbx_list_next(itHistory);
}
bctbx_list_free_with_data(history, (bctbx_list_free_func)linphone_event_log_unref);
size_t marieCrNo = bctbx_list_size(linphone_core_get_chat_rooms(marie1->lc));
BC_ASSERT_EQUAL(marieCrNo, 1, size_t, "%0zu");
size_t laureCrNo = bctbx_list_size(linphone_core_get_chat_rooms(laure->lc));
BC_ASSERT_EQUAL(laureCrNo, 1, size_t, "%0zu");
paulineCrNo = bctbx_list_size(linphone_core_get_chat_rooms(pauline1->lc));
BC_ASSERT_EQUAL(paulineCrNo, 1, size_t, "%0zu");
end:
// Clean db from chat room
if (marie1Cr) linphone_core_manager_delete_chat_room(marie1, marie1Cr, coresList);
if (newPauline1Cr) linphone_core_manager_delete_chat_room(pauline1, newPauline1Cr, coresList);
if (laureCr) linphone_core_manager_delete_chat_room(laure, laureCr, coresList);
// now GC is cleaning old chatroom
if (pauline1Cr) linphone_chat_room_unref(pauline1Cr);
marieCrNo = bctbx_list_size(linphone_core_get_chat_rooms(marie1->lc));
BC_ASSERT_EQUAL(marieCrNo, 0, size_t, "%0zu");
BC_ASSERT_TRUE(wait_for_list(coresList, &marie1->stat.number_of_LinphoneConferenceStateDeleted, 1,
liblinphone_tester_sip_timeout));
laureCrNo = bctbx_list_size(linphone_core_get_chat_rooms(laure->lc));
BC_ASSERT_EQUAL(laureCrNo, 0, size_t, "%0zu");
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_LinphoneConferenceStateDeleted, 1,
liblinphone_tester_sip_timeout));
paulineCrNo = bctbx_list_size(linphone_core_get_chat_rooms(pauline1->lc));
BC_ASSERT_EQUAL(paulineCrNo, 0, size_t, "%0zu");
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline1->stat.number_of_LinphoneConferenceStateDeleted, 2,
liblinphone_tester_sip_timeout));
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
bctbx_list_free_with_data(participantsAddresses, (bctbx_list_free_func)linphone_address_unref);
linphone_core_manager_destroy(marie1);
linphone_core_manager_destroy(pauline1);
linphone_core_manager_destroy(laure);
}
8191819281938194819581968197819881998200820182028203820482058206820782088209821082118212821382148215821682178218821982208221822282238224822582268227822882298230823182328233823482358236823782388239824082418242824382448245824682478248824982508251825282538254825582568257825882598260
static void group_chat_room_join_one_to_one_chat_room_with_a_new_device_not_notified(void) {
LinphoneCoreManager *marie1 = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *marie2 = NULL;
LinphoneChatRoom *marie1Cr = NULL, *marie2Cr = NULL, *paulineCr = NULL;
LinphoneAddress *confAddr = NULL;
bctbx_list_t *coresManagerList = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie1);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
bctbx_list_t *coresList = init_core_for_conference_with_groupchat_version(coresManagerList, "1.0");
start_core_for_conference(coresManagerList);
bctbx_list_t *participantsAddresses =
bctbx_list_append(NULL, linphone_address_new(linphone_core_get_identity(pauline->lc)));
stats initialMarie1Stats = marie1->stat;
stats initialPaulineStats = pauline->stat;
// Marie1 creates a new one-to-one chat room with Pauline
const char *initialSubject = "Pauline";
marie1Cr = create_chat_room_client_side(coresList, marie1, &initialMarie1Stats, participantsAddresses,
initialSubject, FALSE, LinphoneChatRoomEphemeralModeDeviceManaged);
if (!BC_ASSERT_PTR_NOT_NULL(marie1Cr)) goto end;
BC_ASSERT_TRUE(linphone_chat_room_get_capabilities(marie1Cr) & LinphoneChatRoomCapabilitiesOneToOne);
confAddr = (LinphoneAddress *)linphone_chat_room_get_conference_address(marie1Cr);
if (!BC_ASSERT_PTR_NOT_NULL(confAddr)) goto end;
confAddr = linphone_address_clone(confAddr);
// Check that the chat room is correctly created on Pauline's side and that the participants are added
paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats, confAddr, initialSubject,
1, FALSE);
if (!BC_ASSERT_PTR_NOT_NULL(paulineCr)) goto end;
BC_ASSERT_TRUE(linphone_chat_room_get_capabilities(paulineCr) & LinphoneChatRoomCapabilitiesOneToOne);
initialPaulineStats.number_of_participant_devices_added = pauline->stat.number_of_participant_devices_added;
marie2 = linphone_core_manager_create("marie_rc");
stats initialMarie2Stats = marie2->stat;
bctbx_list_t *newCoresManagerList = bctbx_list_append(NULL, marie2);
bctbx_list_t *newCoresList = init_core_for_conference_with_groupchat_version(newCoresManagerList, "1.0");
start_core_for_conference(newCoresManagerList);
coresManagerList = bctbx_list_concat(coresManagerList, newCoresManagerList);
coresList = bctbx_list_concat(coresList, newCoresList);
// Marie2 gets the one-to-one chat room with Pauline
marie2Cr = check_creation_chat_room_client_side(coresList, marie2, &initialMarie2Stats, confAddr, initialSubject, 1,
FALSE);
if (!BC_ASSERT_PTR_NOT_NULL(marie2Cr)) goto end;
BC_ASSERT_TRUE(linphone_chat_room_get_capabilities(marie2Cr) & LinphoneChatRoomCapabilitiesOneToOne);
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_participant_devices_added,
initialPaulineStats.number_of_participant_devices_added + 1,
liblinphone_tester_sip_timeout));
// Save pauline db
const char *uri = linphone_config_get_string(linphone_core_get_config(pauline->lc), "storage", "uri", "");
char *uriCopy = bc_tester_file("linphone_tester.db");
BC_ASSERT_FALSE(liblinphone_tester_copy_file(uri, uriCopy));
int initialPaulineEvent = linphone_chat_room_get_history_events_size(paulineCr);
// Simulate an uninstall of the application on Marie's side with unregistration (It should remove the device)
// Save the number of chat rooms at the moment of stopping the core
const int marie1_no_cr = (int)bctbx_list_size(linphone_core_get_chat_rooms(marie1->lc));
coresManagerList = bctbx_list_remove(coresManagerList, marie1);
coresList = bctbx_list_remove(coresList, marie1->lc);
initialPaulineStats = pauline->stat;
linphone_core_manager_stop(marie1);
// force flexisip to publish on marie topic
linphone_core_refresh_registers(marie2->lc);
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_participant_devices_removed,
8261826282638264826582668267826882698270827182728273827482758276827782788279828082818282828382848285828682878288828982908291829282938294829582968297829882998300830183028303830483058306830783088309831083118312831383148315831683178318831983208321832283238324832583268327832883298330
initialPaulineStats.number_of_participant_devices_removed + 1,
liblinphone_tester_sip_timeout));
// Reset db at pauline side
pauline->database_path = uriCopy;
coresList = bctbx_list_remove(coresList, pauline->lc);
memset(&initialPaulineStats, 0, sizeof(initialPaulineStats));
linphone_core_manager_reinit(pauline);
// force full state
linphone_config_set_bool(linphone_core_get_config(pauline->lc), "misc", "conference_event_package_force_full_state",
TRUE);
bctbx_list_t *tmpCoresManagerList = bctbx_list_append(NULL, pauline);
bctbx_list_t *tmpCoresList = init_core_for_conference_with_groupchat_version(tmpCoresManagerList, "1.0");
bctbx_list_free(tmpCoresManagerList);
coresList = bctbx_list_concat(coresList, tmpCoresList);
linphone_core_manager_start(pauline, TRUE);
// wait for first notify to be received by pauline
wait_for_list(coresList, NULL, 0, 1000);
// Marie2 gets the one-to-one chat room with Pauline
paulineCr =
check_has_chat_room_client_side(coresList, pauline, &initialPaulineStats, confAddr, initialSubject, 1, FALSE);
LinphoneAddress *marieAddress = linphone_address_new(linphone_core_get_identity(marie2->lc));
LinphoneParticipant *marieParticipant = linphone_chat_room_find_participant(paulineCr, marieAddress);
BC_ASSERT_EQUAL((int)bctbx_list_size(linphone_participant_get_devices(marieParticipant)), 1, int, "%i");
// recheck after restart
coresList = bctbx_list_remove(coresList, pauline->lc);
linphone_core_manager_reinit(pauline);
linphone_config_set_bool(linphone_core_get_config(pauline->lc), "misc", "conference_event_package_force_full_state",
FALSE);
tmpCoresManagerList = bctbx_list_append(NULL, pauline);
tmpCoresList = init_core_for_conference_with_groupchat_version(tmpCoresManagerList, "1.0");
bctbx_list_free(tmpCoresManagerList);
coresList = bctbx_list_concat(coresList, tmpCoresList);
linphone_core_manager_start(pauline, TRUE);
// wait for first notify to be received by pauline
wait_for_list(coresList, NULL, 0, 1000);
// Marie2 gets the one-to-one chat room with Pauline
paulineCr =
check_has_chat_room_client_side(coresList, pauline, &initialPaulineStats, confAddr, initialSubject, 1, FALSE);
marieParticipant = linphone_chat_room_find_participant(paulineCr, marieAddress);
BC_ASSERT_EQUAL((int)bctbx_list_size(linphone_participant_get_devices(marieParticipant)), 1, int, "%i");
BC_ASSERT_EQUAL(linphone_chat_room_get_history_events_size(paulineCr), initialPaulineEvent, int, "%i");
// check if we can still communicate
// Marie1 sends a message
const char *textMessage = "Hello";
LinphoneChatMessage *message = _send_message(marie2Cr, textMessage);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie2->stat.number_of_LinphoneMessageDelivered,
initialMarie1Stats.number_of_LinphoneMessageDelivered + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageReceived,
initialPaulineStats.number_of_LinphoneMessageReceived + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_STRING_EQUAL(linphone_chat_message_get_text(pauline->stat.last_received_chat_message), textMessage);
linphone_chat_message_unref(message);
// Pauline answers to the previous message
textMessage = "Hey. How are you?";
message = _send_message(paulineCr, textMessage);
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageDelivered,
initialPaulineStats.number_of_LinphoneMessageDelivered + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &marie2->stat.number_of_LinphoneMessageReceived,
initialMarie1Stats.number_of_LinphoneMessageReceived + 1,
8331833283338334833583368337833883398340834183428343834483458346834783488349835083518352835383548355835683578358835983608361836283638364836583668367836883698370837183728373837483758376837783788379838083818382838383848385838683878388838983908391839283938394839583968397839883998400
liblinphone_tester_sip_timeout));
BC_ASSERT_STRING_EQUAL(linphone_chat_message_get_text(marie2->stat.last_received_chat_message), textMessage);
linphone_chat_message_unref(message);
// Clean db from chat room
linphone_core_manager_reinit(marie1);
tmpCoresManagerList = bctbx_list_append(NULL, marie1);
tmpCoresList = init_core_for_conference_with_groupchat_version(tmpCoresManagerList, "1.0");
bctbx_list_free(tmpCoresManagerList);
coresList = bctbx_list_concat(coresList, tmpCoresList);
linphone_core_manager_start(marie1, TRUE);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie1->stat.number_of_LinphoneConferenceStateCreated,
initialMarie1Stats.number_of_LinphoneConferenceStateCreated + marie1_no_cr,
liblinphone_tester_sip_timeout));
wait_for_list(coresList, NULL, 0, 1000);
marie1Cr =
check_has_chat_room_client_side(coresList, marie1, &initialMarie1Stats, confAddr, initialSubject, 1, FALSE);
end:
if (marie1Cr) linphone_core_manager_delete_chat_room(marie1, marie1Cr, coresList);
if (marie2Cr) linphone_core_manager_delete_chat_room(marie2, marie2Cr, coresList);
if (paulineCr) linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
if (confAddr) linphone_address_unref(confAddr);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie1);
if (marie2) linphone_core_manager_destroy(marie2);
linphone_core_manager_destroy(pauline);
}
static void subscribe_test_after_set_chat_database_path(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *laure = linphone_core_manager_create("laure_tcp_rc");
LinphoneChatRoom *marieCr = NULL, *paulineCr = NULL, *laureCr = NULL;
const LinphoneAddress *confAddr = NULL;
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
coresManagerList = bctbx_list_append(coresManagerList, laure);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(laure->lc)));
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
stats initialLaureStats = laure->stat;
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
marieCr = create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject,
FALSE, LinphoneChatRoomEphemeralModeDeviceManaged);
if (!BC_ASSERT_PTR_NOT_NULL(marieCr)) goto end;
confAddr = linphone_chat_room_get_conference_address(marieCr);
if (!BC_ASSERT_PTR_NOT_NULL(confAddr)) goto end;
// Check that the chat room is correctly created on Pauline's side and that the participants are added
paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats, confAddr, initialSubject,
2, FALSE);
if (!BC_ASSERT_PTR_NOT_NULL(paulineCr)) goto end;
// Check that the chat room is correctly created on Laure's side and that the participants are added
laureCr =
check_creation_chat_room_client_side(coresList, laure, &initialLaureStats, confAddr, initialSubject, 2, FALSE);
8401840284038404840584068407840884098410841184128413841484158416841784188419842084218422842384248425842684278428842984308431843284338434843584368437843884398440844184428443844484458446844784488449845084518452845384548455845684578458845984608461846284638464846584668467846884698470
if (!BC_ASSERT_PTR_NOT_NULL(laureCr)) goto end;
linphone_core_manager_reinit(pauline);
coresList = NULL;
coresList = bctbx_list_append(coresList, marie->lc);
coresList = bctbx_list_append(coresList, pauline->lc);
coresList = bctbx_list_append(coresList, laure->lc);
LinphoneAddress *factoryAddr = linphone_address_new(sFactoryUri);
_configure_core_for_conference(pauline, factoryAddr);
linphone_address_unref(factoryAddr);
LinphoneCoreCbs *cbs = linphone_factory_create_core_cbs(linphone_factory_get());
linphone_core_cbs_set_chat_room_state_changed(cbs, core_chat_room_state_changed);
configure_core_for_callbacks(pauline, cbs);
linphone_core_cbs_unref(cbs);
linphone_core_manager_start(pauline, TRUE);
LinphoneAddress *paulineAddress =
linphone_address_clone(linphone_proxy_config_get_contact(linphone_core_get_default_proxy_config(pauline->lc)));
paulineCr = linphone_core_find_chat_room(pauline->lc, confAddr, paulineAddress);
BC_ASSERT_PTR_NOT_NULL(paulineCr);
linphone_chat_room_ref(paulineCr);
linphone_core_set_network_reachable(pauline->lc, FALSE);
const char *path = "";
// set_chat_database_path() will cause a reload of the database, with re-creation of chatrooms.
linphone_core_set_chat_database_path(pauline->lc, path);
if (paulineCr) linphone_chat_room_unref(paulineCr);
paulineCr = linphone_core_find_chat_room(pauline->lc, confAddr, paulineAddress);
linphone_address_unref(paulineAddress);
linphone_core_set_network_reachable(pauline->lc, TRUE);
// Marie now changes the subject
const char *newSubject = "Subject has been changed! :O";
linphone_chat_room_set_subject(marieCr, newSubject);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_subject_changed,
initialMarieStats.number_of_subject_changed + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_subject_changed,
initialPaulineStats.number_of_subject_changed + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_subject_changed,
initialLaureStats.number_of_subject_changed + 1, liblinphone_tester_sip_timeout));
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(marieCr), newSubject);
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(paulineCr), newSubject);
BC_ASSERT_STRING_EQUAL(linphone_chat_room_get_subject(laureCr), newSubject);
end:
// Clean db from chat room
if (marieCr) linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
if (laureCr) linphone_core_manager_delete_chat_room(laure, laureCr, coresList);
if (paulineCr) linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
linphone_core_manager_destroy(laure);
}
static void one_to_one_chat_room_send_forward_message(void) {
group_chat_room_unique_one_to_one_chat_room_with_forward_message_recreated_from_message_base(FALSE, TRUE, FALSE);
}
static void one_to_one_chat_room_send_forward_message_with_restart(void) {
group_chat_room_unique_one_to_one_chat_room_with_forward_message_recreated_from_message_base(TRUE, TRUE, FALSE);
}
static void one_to_one_chat_room_reply_forward_message(void) {
group_chat_room_unique_one_to_one_chat_room_with_forward_message_recreated_from_message_base(FALSE, FALSE, TRUE);
}
8471847284738474847584768477847884798480848184828483848484858486848784888489849084918492849384948495849684978498849985008501850285038504850585068507850885098510851185128513851485158516851785188519852085218522852385248525852685278528852985308531853285338534853585368537853885398540
static void one_to_one_chat_room_reply_forward_message_with_restart(void) {
group_chat_room_unique_one_to_one_chat_room_with_forward_message_recreated_from_message_base(TRUE, FALSE, TRUE);
}
static void core_stop_start_with_chat_room_ref(void) {
LinphoneCoreManager *marie1 = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline1 = linphone_core_manager_create("pauline_rc");
LinphoneChatRoom *marie1Cr = NULL, *pauline1Cr = NULL, *newPauline1Cr = NULL;
const LinphoneAddress *confAddr = NULL;
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie1);
coresManagerList = bctbx_list_append(coresManagerList, pauline1);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline1->lc)));
stats initialMarie1Stats = marie1->stat;
stats initialPauline1Stats = pauline1->stat;
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
marie1Cr = create_chat_room_client_side(coresList, marie1, &initialMarie1Stats, participantsAddresses,
initialSubject, FALSE, LinphoneChatRoomEphemeralModeDeviceManaged);
if (!BC_ASSERT_PTR_NOT_NULL(marie1Cr)) goto end;
participantsAddresses = NULL;
confAddr = linphone_chat_room_get_conference_address(marie1Cr);
if (!BC_ASSERT_PTR_NOT_NULL(confAddr)) goto end;
// Check that the chat room is correctly created on Pauline1
pauline1Cr = check_creation_chat_room_client_side(coresList, pauline1, &initialPauline1Stats, confAddr,
initialSubject, 1, FALSE);
if (!BC_ASSERT_PTR_NOT_NULL(pauline1Cr)) goto end;
// Pauline leaving but keeping a ref like a Java GC can do, this is the key part of this test.
linphone_chat_room_ref(pauline1Cr);
linphone_core_stop(pauline1->lc);
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline1->stat.number_of_LinphoneGlobalShutdown,
initialPauline1Stats.number_of_LinphoneGlobalShutdown + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline1->stat.number_of_LinphoneGlobalOff,
initialPauline1Stats.number_of_LinphoneGlobalOff + 1, liblinphone_tester_sip_timeout));
linphone_core_start(pauline1->lc);
// now GC is cleaning old chatroom
if (pauline1Cr) linphone_chat_room_unref(pauline1Cr);
// test very early client group chatroom creation, should fail
LinphoneProxyConfig *proxy = linphone_core_get_default_proxy_config(pauline1->lc);
linphone_proxy_config_edit(proxy);
linphone_proxy_config_set_conference_factory_uri(proxy, sFactoryUri);
linphone_proxy_config_done(proxy);
LinphoneChatRoomParams *params = linphone_core_create_default_chat_room_params(pauline1->lc);
linphone_chat_room_params_set_backend(params, LinphoneChatRoomBackendFlexisipChat);
LinphoneChatRoom *chatRoom =
linphone_core_create_chat_room_2(pauline1->lc, params, initialSubject, participantsAddresses);
linphone_chat_room_params_unref(params);
BC_ASSERT_PTR_NULL(chatRoom);
if (chatRoom) linphone_chat_room_unref(chatRoom);
coresList = bctbx_list_remove(coresList, pauline1->lc);
linphone_core_manager_reinit(pauline1);
bctbx_list_t *tmpCoresManagerList = bctbx_list_append(NULL, pauline1);
bctbx_list_t *tmpCoresList = init_core_for_conference(tmpCoresManagerList);
bctbx_list_free(tmpCoresManagerList);
coresList = bctbx_list_concat(coresList, tmpCoresList);
8541854285438544854585468547854885498550855185528553855485558556855785588559856085618562856385648565856685678568856985708571857285738574857585768577857885798580858185828583858485858586858785888589859085918592859385948595859685978598859986008601860286038604860586068607860886098610
linphone_core_manager_start(pauline1, TRUE);
// Check that the chat room has correctly created on Laure's side and that the participants are added
newPauline1Cr =
check_has_chat_room_client_side(coresList, pauline1, &initialPauline1Stats, confAddr, initialSubject, 1, FALSE);
wait_for_list(coresList, NULL, 0, 1000);
end:
// Clean db from chat room
if (marie1Cr) linphone_core_manager_delete_chat_room(marie1, marie1Cr, coresList);
if (newPauline1Cr) linphone_core_manager_delete_chat_room(pauline1, newPauline1Cr, coresList);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
bctbx_list_free_with_data(participantsAddresses, (bctbx_list_free_func)linphone_address_unref);
linphone_core_manager_destroy(marie1);
linphone_core_manager_destroy(pauline1);
}
static void group_chat_room_device_unregistered(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *laure = linphone_core_manager_create("laure_tcp_rc");
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
coresManagerList = bctbx_list_append(coresManagerList, laure);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(laure->lc)));
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
stats initialLaureStats = laure->stat;
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
LinphoneChatRoom *marieCr =
create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject, FALSE,
LinphoneChatRoomEphemeralModeDeviceManaged);
participantsAddresses = NULL;
const LinphoneAddress *confAddr = linphone_chat_room_get_conference_address(marieCr);
// Check that the chat room is correctly created on Pauline's side and that the participants are added
LinphoneChatRoom *paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats,
confAddr, initialSubject, 2, FALSE);
// Check that the chat room is correctly created on Laure's side and that the participants are added
LinphoneChatRoom *laureCr =
check_creation_chat_room_client_side(coresList, laure, &initialLaureStats, confAddr, initialSubject, 2, FALSE);
LinphoneProxyConfig *proxyConfig = linphone_core_get_default_proxy_config(laure->lc);
linphone_proxy_config_edit(proxyConfig);
linphone_proxy_config_enable_register(proxyConfig, FALSE);
linphone_proxy_config_done(proxyConfig);
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_LinphoneRegistrationCleared,
initialMarieStats.number_of_LinphoneRegistrationCleared + 1,
liblinphone_tester_sip_timeout));
// Current expected behavior is to have participant devices removed
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_participant_devices_removed,
initialMarieStats.number_of_participant_devices_removed + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_participant_devices_removed,
initialPaulineStats.number_of_participant_devices_removed + 1,
liblinphone_tester_sip_timeout));
8611861286138614861586168617861886198620862186228623862486258626862786288629863086318632863386348635863686378638863986408641864286438644864586468647864886498650865186528653865486558656865786588659866086618662866386648665866686678668866986708671867286738674867586768677867886798680
BC_ASSERT_FALSE(wait_for_list(coresList, &marie->stat.number_of_participants_removed,
initialMarieStats.number_of_participants_removed + 1, 3000));
BC_ASSERT_FALSE(wait_for_list(coresList, &pauline->stat.number_of_participants_removed,
initialPaulineStats.number_of_participants_removed + 1, 3000));
// to avoid automatique re-subscription of chatroom while disabling network
linphone_core_enter_background(marie->lc);
linphone_core_enter_background(pauline->lc);
linphone_core_enter_background(laure->lc);
wait_for_list(coresList, NULL, 1, 3000);
// to force re-re-connection to restarted flexisip
linphone_core_set_network_reachable(marie->lc, FALSE);
linphone_core_set_network_reachable(pauline->lc, FALSE);
linphone_core_set_network_reachable(laure->lc, FALSE);
// break here and restart Flexisip
marie->stat.number_of_participant_devices_added = 0;
pauline->stat.number_of_participant_devices_added = 0;
proxyConfig = linphone_core_get_default_proxy_config(laure->lc);
linphone_proxy_config_edit(proxyConfig);
linphone_proxy_config_enable_register(proxyConfig, TRUE);
linphone_proxy_config_done(proxyConfig);
linphone_core_enter_foreground(marie->lc);
linphone_core_set_network_reachable(marie->lc, TRUE);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneRegistrationOk,
initialMarieStats.number_of_LinphoneRegistrationOk + 1, 10000));
linphone_core_enter_foreground(pauline->lc);
linphone_core_set_network_reachable(pauline->lc, TRUE);
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneRegistrationOk,
initialPaulineStats.number_of_LinphoneRegistrationOk + 1, 10000));
linphone_core_enter_foreground(laure->lc);
linphone_core_set_network_reachable(laure->lc, TRUE);
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_LinphoneRegistrationOk,
initialLaureStats.number_of_LinphoneRegistrationOk + 1, 10000));
// in case of flexisip restart
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_participant_devices_added,
initialMarieStats.number_of_participant_devices_added + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_participant_devices_added,
initialPaulineStats.number_of_participant_devices_added + 1,
liblinphone_tester_sip_timeout));
// Laure adds a new device without group chat enabled
initialMarieStats = marie->stat;
initialPaulineStats = pauline->stat;
initialLaureStats = laure->stat;
LinphoneCoreManager *laure2 = linphone_core_manager_new("laure_tcp_rc");
coresManagerList = bctbx_list_append(coresManagerList, laure2);
proxyConfig = linphone_core_get_default_proxy_config(laure->lc);
linphone_proxy_config_edit(proxyConfig);
linphone_proxy_config_enable_register(proxyConfig, FALSE);
linphone_proxy_config_done(proxyConfig);
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_LinphoneRegistrationCleared,
initialLaureStats.number_of_LinphoneRegistrationCleared + 1,
liblinphone_tester_sip_timeout));
// Current expected behavior is to have participant devices removed
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_participant_devices_removed,
initialMarieStats.number_of_participant_devices_removed + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_participant_devices_removed,
initialPaulineStats.number_of_participant_devices_removed + 1,
liblinphone_tester_sip_timeout));
8681868286838684868586868687868886898690869186928693869486958696869786988699870087018702870387048705870687078708870987108711871287138714871587168717871887198720872187228723872487258726872787288729873087318732873387348735873687378738873987408741874287438744874587468747874887498750
BC_ASSERT_FALSE(wait_for_list(coresList, &marie->stat.number_of_participants_removed,
initialMarieStats.number_of_participants_removed + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_FALSE(wait_for_list(coresList, &pauline->stat.number_of_participants_removed,
initialPaulineStats.number_of_participants_removed + 1,
liblinphone_tester_sip_timeout));
// Clean db from chat room
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
linphone_core_manager_delete_chat_room(laure, laureCr, coresList);
linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
linphone_core_manager_destroy(laure);
linphone_core_manager_destroy(laure2);
}
static void group_chat_room_admin_creator_leaves_and_is_reinvited(void) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
LinphoneCoreManager *laure = linphone_core_manager_create("laure_tcp_rc");
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
coresManagerList = bctbx_list_append(coresManagerList, laure);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(laure->lc)));
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
stats initialLaureStats = laure->stat;
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
LinphoneChatRoom *marieCr =
create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject, FALSE,
LinphoneChatRoomEphemeralModeDeviceManaged);
const LinphoneAddress *confAddr = linphone_chat_room_get_conference_address(marieCr);
// Check that the chat room is correctly created on Pauline's side and that the participants are added
LinphoneChatRoom *paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats,
confAddr, initialSubject, 2, FALSE);
// Check that the chat room is correctly created on Laure's side and that the participants are added
LinphoneChatRoom *laureCr =
check_creation_chat_room_client_side(coresList, laure, &initialLaureStats, confAddr, initialSubject, 2, FALSE);
// Marie leaves the room
linphone_chat_room_leave(marieCr);
BC_ASSERT_TRUE(wait_for_list(coresList, &marie->stat.number_of_LinphoneConferenceStateTerminated,
initialMarieStats.number_of_LinphoneConferenceStateTerminated + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_participants_removed,
initialPaulineStats.number_of_participants_removed + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_participants_removed,
initialLaureStats.number_of_participants_removed + 1, liblinphone_tester_sip_timeout));
/* FIXME: the number of admin status changed shoud be 1. But the conference server notifies first that marie looses
* its admin status, before being deleted from the chatroom. This is indeed useless to notify this. Once fixed in
* the conference server, the counter shall be set back to +1. */
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_participant_admin_statuses_changed,
8751875287538754875587568757875887598760876187628763876487658766876787688769877087718772877387748775877687778778877987808781878287838784878587868787878887898790879187928793879487958796879787988799880088018802880388048805880688078808880988108811881288138814881588168817881888198820
initialPaulineStats.number_of_participant_admin_statuses_changed + 2,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &laure->stat.number_of_participant_admin_statuses_changed,
initialLaureStats.number_of_participant_admin_statuses_changed + 2,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(linphone_participant_is_admin(linphone_chat_room_get_me(laureCr)));
linphone_core_delete_chat_room(marie->lc, marieCr);
initialMarieStats = marie->stat;
// Laure invites Marie to the chatroom
participantsAddresses = NULL;
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(marie->lc)));
linphone_chat_room_add_participants(laureCr, participantsAddresses);
bctbx_list_free_with_data(participantsAddresses, (bctbx_list_free_func)linphone_address_unref);
participantsAddresses = NULL;
// Check that the chat room is correctly created on Marie's side and that the participants are added
marieCr = check_creation_chat_room_client_side(coresList, marie, &initialMarieStats,
linphone_chat_room_get_conference_address(laureCr), initialSubject,
2, FALSE);
// Clean db from chat room
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
linphone_core_manager_delete_chat_room(laure, laureCr, coresList);
linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
linphone_core_manager_destroy(laure);
}
static void group_chat_forward_file_transfer_message_url(const char *file_transfer_server_url) {
LinphoneCoreManager *marie = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
char *sendFilepath = bc_tester_res("sounds/sintel_trailer_opus_h264.mkv");
char *receivePaulineFilepath = bc_tester_file("receive_file_pauline.dump");
char *receiveMarieFilepath = bc_tester_file("receive_file_marie.dump");
/* Remove any previously downloaded file */
remove(receivePaulineFilepath);
remove(receiveMarieFilepath);
coresManagerList = bctbx_list_append(coresManagerList, marie);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
linphone_core_set_file_transfer_server(marie->lc, file_transfer_server_url);
linphone_core_set_file_transfer_server(pauline->lc, file_transfer_server_url);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
stats initialMarieStats = marie->stat;
stats initialPaulineStats = pauline->stat;
// Marie creates a new group chat room
const char *initialSubject = "Pauline";
LinphoneChatRoom *marieCr =
create_chat_room_client_side(coresList, marie, &initialMarieStats, participantsAddresses, initialSubject, FALSE,
LinphoneChatRoomEphemeralModeDeviceManaged);
const LinphoneAddress *confAddr = linphone_chat_room_get_conference_address(marieCr);
// Check that the chat room is correctly created on Pauline's side and that the participants are added
LinphoneChatRoom *paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats,
8821882288238824882588268827882888298830883188328833883488358836883788388839884088418842884388448845884688478848884988508851885288538854885588568857885888598860886188628863886488658866886788688869887088718872887388748875887688778878887988808881888288838884888588868887888888898890
confAddr, initialSubject, 1, FALSE);
BC_ASSERT_TRUE(linphone_chat_room_get_capabilities(paulineCr) & LinphoneChatRoomCapabilitiesOneToOne);
// Marie sends a message
_send_file(marieCr, sendFilepath, NULL, FALSE);
// Check pauline got it
// Note: we must not use the buffer reception(last param to FALSE) or our message transfer won't work, probably some
// fix to be done in the callback
_receive_file(coresList, pauline, &initialPaulineStats, receivePaulineFilepath, sendFilepath, NULL, FALSE);
// Retrieve message from Pauline chatroom history
BC_ASSERT_EQUAL(linphone_chat_room_get_history_size(paulineCr), 1, int, " %i");
if (linphone_chat_room_get_history_size(paulineCr) > 0) {
bctbx_list_t *history = linphone_chat_room_get_history(paulineCr, 1);
LinphoneChatMessage *recv_msg = (LinphoneChatMessage *)(history->data);
// Forward it to Marie
LinphoneChatMessage *msg = linphone_chat_room_create_forward_message(paulineCr, recv_msg);
const LinphoneAddress *forwarded_from_address = linphone_chat_message_get_from_address(recv_msg);
char *forwarded_from = linphone_address_as_string_uri_only(forwarded_from_address);
bctbx_list_free_with_data(history, (bctbx_list_free_func)linphone_chat_message_unref);
LinphoneChatMessageCbs *cbs = linphone_chat_message_get_callbacks(msg);
linphone_chat_message_cbs_set_msg_state_changed(cbs, liblinphone_tester_chat_message_msg_state_changed);
linphone_chat_message_send(msg);
BC_ASSERT_TRUE(linphone_chat_message_is_forward(msg));
BC_ASSERT_STRING_EQUAL(linphone_chat_message_get_forward_info(msg), forwarded_from);
// Check Marie received it and that the file is still the same
_receive_file(coresList, marie, &initialMarieStats, receiveMarieFilepath, sendFilepath, NULL, FALSE);
linphone_chat_message_unref(msg);
ms_free(forwarded_from);
} else {
BC_FAIL("Could not get message to forward from history");
}
// Clean db from chat room
linphone_core_manager_delete_chat_room(marie, marieCr, coresList);
linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
wait_for_list(coresList, 0, 1, 2000);
BC_ASSERT_EQUAL(linphone_core_get_call_history_size(marie->lc), 0, int, "%i");
BC_ASSERT_EQUAL(linphone_core_get_call_history_size(pauline->lc), 0, int, "%i");
BC_ASSERT_PTR_NULL(linphone_core_get_call_logs(marie->lc));
BC_ASSERT_PTR_NULL(linphone_core_get_call_logs(pauline->lc));
ms_free(sendFilepath);
ms_free(receivePaulineFilepath);
ms_free(receiveMarieFilepath);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie);
linphone_core_manager_destroy(pauline);
}
static void group_chat_forward_file_transfer_message(void) {
group_chat_forward_file_transfer_message_url(file_transfer_url);
}
static void group_chat_forward_file_transfer_message_digest_auth_server(void) {
group_chat_forward_file_transfer_message_url(file_transfer_url_digest_auth);
}
static void group_chat_forward_file_transfer_message_digest_auth_server_encryptedFS(void) {
uint8_t evfs_key[32] = {0xaa, 0x55, 0xFF, 0xFF, 0x12, 0x34, 0x56, 0x78, 0x9a, 0xbc, 0xde,
0xf0, 0x11, 0x22, 0x33, 0x44, 0x5a, 0xa5, 0x5F, 0xaF, 0x52, 0xa4,
8891889288938894889588968897889888998900890189028903890489058906890789088909891089118912891389148915891689178918891989208921892289238924892589268927892889298930893189328933893489358936893789388939894089418942894389448945894689478948894989508951895289538954895589568957895889598960
0xa6, 0x58, 0xaa, 0x5c, 0xae, 0x50, 0xa1, 0x52, 0xa3, 0x54};
linphone_factory_set_vfs_encryption(linphone_factory_get(), LINPHONE_VFS_ENCRYPTION_AES256GCM128_SHA256, evfs_key,
32);
group_chat_forward_file_transfer_message_url(file_transfer_url_digest_auth);
linphone_factory_set_vfs_encryption(linphone_factory_get(), LINPHONE_VFS_ENCRYPTION_UNSET, NULL, 0);
}
static void group_chat_room_message_sync_between_devices_with_same_identity(void) {
LinphoneCoreManager *marie1 = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *marie2 = linphone_core_manager_create("marie_rc");
LinphoneCoreManager *pauline = linphone_core_manager_create("pauline_rc");
bctbx_list_t *coresManagerList = NULL;
bctbx_list_t *participantsAddresses = NULL;
coresManagerList = bctbx_list_append(coresManagerList, marie1);
coresManagerList = bctbx_list_append(coresManagerList, marie2);
coresManagerList = bctbx_list_append(coresManagerList, pauline);
bctbx_list_t *coresList = init_core_for_conference(coresManagerList);
start_core_for_conference(coresManagerList);
participantsAddresses =
bctbx_list_append(participantsAddresses, linphone_address_new(linphone_core_get_identity(pauline->lc)));
stats initialMarie1Stats = marie1->stat;
stats initialMarie2Stats = marie2->stat;
stats initialPaulineStats = pauline->stat;
// Marie creates a new group chat room
const char *initialSubject = "Colleagues";
LinphoneChatRoom *marie1Cr =
create_chat_room_client_side(coresList, marie1, &initialMarie1Stats, participantsAddresses, initialSubject,
FALSE, LinphoneChatRoomEphemeralModeDeviceManaged);
BC_ASSERT_PTR_NOT_NULL(marie1Cr);
const LinphoneAddress *confAddr = linphone_chat_room_get_conference_address(marie1Cr);
// Check that the chat room is correctly created on Pauline's side and that the participants are added
LinphoneChatRoom *paulineCr = check_creation_chat_room_client_side(coresList, pauline, &initialPaulineStats,
confAddr, initialSubject, 1, FALSE);
BC_ASSERT_PTR_NOT_NULL(paulineCr);
// Check that the chat room is correctly created on Chloe's side and that the participants are added
LinphoneChatRoom *marie2Cr = check_creation_chat_room_client_side(coresList, marie2, &initialMarie2Stats, confAddr,
initialSubject, 1, FALSE);
BC_ASSERT_PTR_NOT_NULL(marie2Cr);
// Marie2 won't send 200OK to flexisip when receiving it's own outgoing message from marie1
sal_set_send_error(linphone_core_get_sal(marie2->lc), -1); // to trash 200ok without generating error
const char *marie1TextMessage = "Hum.";
LinphoneChatMessage *marie1Message = _send_message(marie1Cr, marie1TextMessage);
BC_ASSERT_TRUE(wait_for_list(coresList, &pauline->stat.number_of_LinphoneMessageReceived,
initialPaulineStats.number_of_LinphoneMessageReceived + 1,
liblinphone_tester_sip_timeout));
BC_ASSERT_TRUE(wait_for_list(coresList, &marie2->stat.number_of_LinphoneMessageReceived,
initialMarie2Stats.number_of_LinphoneMessageReceived + 1,
liblinphone_tester_sip_timeout));
linphone_chat_message_unref(marie1Message);
wait_for_list(coresList, NULL, 0, 1000);
// Marie2 will now receive the message again but this time it will acknowledge it
sal_set_send_error(linphone_core_get_sal(marie2->lc), 0);
linphone_core_refresh_registers(marie2->lc);
// Check that the duplicate is detected and we are not notified of it, not it is stored in DB
BC_ASSERT_FALSE(wait_for_list(coresList, &marie2->stat.number_of_LinphoneMessageReceived,
initialMarie2Stats.number_of_LinphoneMessageReceived + 2,
liblinphone_tester_sip_timeout));
bctbx_list_t *messages = linphone_chat_room_get_history(marie2Cr, 0);
8961896289638964896589668967896889698970897189728973897489758976897789788979898089818982898389848985898689878988898989908991899289938994899589968997899889999000900190029003900490059006900790089009901090119012901390149015901690179018901990209021902290239024902590269027902890299030
int count = (int)(bctbx_list_size(messages));
BC_ASSERT_EQUAL(count, 1, int, "%d");
bctbx_list_free_with_data(messages, (bctbx_list_free_func)linphone_chat_message_unref);
// Clean db from chat room
linphone_core_manager_delete_chat_room(marie1, marie1Cr, coresList);
linphone_core_manager_delete_chat_room(marie2, marie2Cr, coresList);
linphone_core_manager_delete_chat_room(pauline, paulineCr, coresList);
bctbx_list_free(coresList);
bctbx_list_free(coresManagerList);
linphone_core_manager_destroy(marie1);
linphone_core_manager_destroy(marie2);
linphone_core_manager_destroy(pauline);
}
test_t group_chat_tests[] = {
TEST_NO_TAG("Chat room params", group_chat_room_params),
TEST_ONE_TAG("Core restarts as soon as chat room is created", group_chat_room_creation_core_restart, "LeaksMemory"),
TEST_NO_TAG("Chat room with forced local identity", group_chat_room_creation_with_given_identity),
TEST_NO_TAG("Group chat room creation server", group_chat_room_creation_server),
TEST_NO_TAG("Network down while creating group chat room", group_chat_room_creation_server_network_down),
TEST_NO_TAG("Network down/up while creating group chat room", group_chat_room_creation_server_network_down_up),
TEST_ONE_TAG("Add participant", group_chat_room_add_participant, "LeaksMemory"),
TEST_NO_TAG("Send message", group_chat_room_send_message),
TEST_NO_TAG("Send encrypted message", group_chat_room_send_message_encrypted),
TEST_NO_TAG("Send message with error", group_chat_room_send_message_with_error),
TEST_NO_TAG("Send invite on a multi register account", group_chat_room_invite_multi_register_account),
TEST_NO_TAG("Send message check sync between devices",
group_chat_room_message_sync_between_devices_with_same_identity),
TEST_NO_TAG("Add admin", group_chat_room_add_admin),
TEST_NO_TAG("Add admin lately notified", group_chat_room_add_admin_lately_notified),
TEST_NO_TAG("Add admin with a non admin", group_chat_room_add_admin_non_admin),
TEST_NO_TAG("Remove admin", group_chat_room_remove_admin),
TEST_NO_TAG("Admin creator leaves the room", group_chat_room_admin_creator_leaves_the_room),
TEST_NO_TAG("Change subject", group_chat_room_change_subject),
TEST_NO_TAG("Change subject with a non admin", group_chat_room_change_subject_non_admin),
TEST_NO_TAG("Remove participant", group_chat_room_remove_participant),
TEST_ONE_TAG("Remove participant and restart",
group_chat_room_remove_participant_and_restart,
"LeaksMemory"), // Due to core restart
TEST_NO_TAG("Send message with a participant removed", group_chat_room_send_message_with_participant_removed),
TEST_NO_TAG("Leave group chat room", group_chat_room_leave),
TEST_NO_TAG("Delete group chat room successful if it's already removed by server", group_chat_room_delete_twice),
TEST_NO_TAG("Come back on a group chat room after a disconnection", group_chat_room_come_back_after_disconnection),
TEST_NO_TAG("Create chat room with disconnected friends", group_chat_room_create_room_with_disconnected_friends),
TEST_NO_TAG("Create chat room with disconnected friends and initial message",
group_chat_room_create_room_with_disconnected_friends_and_initial_message),
TEST_NO_TAG("Reinvited after removed from group chat room", group_chat_room_reinvited_after_removed)};
test_t group_chat2_tests[] = {
TEST_NO_TAG("Send file + text", group_chat_room_send_file_plus_text),
TEST_NO_TAG("Send 2 files + text", group_chat_room_send_two_files_plus_text),
TEST_NO_TAG("Send multipart message with custom content types",
group_chat_room_send_multipart_custom_content_types),
TEST_NO_TAG("Unique one-to-one chatroom", group_chat_room_unique_one_to_one_chat_room),
TEST_NO_TAG("Unique one-to-one chatroom with dual sender device",
group_chat_room_unique_one_to_one_chat_room_dual_sender_device),
TEST_NO_TAG("Unique one-to-one chatroom recreated from message",
group_chat_room_unique_one_to_one_chat_room_recreated_from_message),
TEST_ONE_TAG("Unique one-to-one chatroom recreated from message with app restart",
group_chat_room_unique_one_to_one_chat_room_recreated_from_message_with_app_restart,
"LeaksMemory"),
TEST_NO_TAG("Join one-to-one chat room with a new device",
group_chat_room_join_one_to_one_chat_room_with_a_new_device),
TEST_NO_TAG("New unique one-to-one chatroom after both participants left",
group_chat_room_new_unique_one_to_one_chat_room_after_both_participants_left),
TEST_NO_TAG("Unique one-to-one chatroom re-created from the party that deleted it, with inactive devices",
group_chat_room_unique_one_to_one_chat_room_recreated_from_message_2),
9031903290339034903590369037903890399040904190429043904490459046904790489049905090519052905390549055905690579058905990609061906290639064906590669067906890699070907190729073907490759076907790789079908090819082908390849085908690879088908990909091909290939094909590969097909890999100
TEST_ONE_TAG("Group chat room notify participant devices name",
group_chat_room_participant_devices_name,
"LeaksMemory" /* Core restarts */),
TEST_NO_TAG("Add device in one-to-one chat room where other participant left",
add_device_one_to_one_chat_room_other_left),
TEST_NO_TAG("IMDN for group chat room", imdn_for_group_chat_room),
TEST_NO_TAG("Aggregated IMDN for group chat room", aggregated_imdn_for_group_chat_room),
TEST_NO_TAG("Aggregated IMDN for group chat room read while offline",
aggregated_imdn_for_group_chat_room_read_while_offline),
TEST_ONE_TAG("IMDN sent from DB state", imdn_sent_from_db_state, "LeaksMemory"),
TEST_NO_TAG("IMDN updated for group chat room with one participant offline",
imdn_updated_for_group_chat_room_with_one_participant_offline),
TEST_NO_TAG("Find one-to-one chat room", find_one_to_one_chat_room),
TEST_NO_TAG("Exhumed one-to-one chat room 1", exhume_one_to_one_chat_room_1),
TEST_NO_TAG("Exhumed one-to-one chat room 2", exhume_one_to_one_chat_room_2),
TEST_NO_TAG("Exhumed one-to-one chat room 3", exhume_one_to_one_chat_room_3),
TEST_ONE_TAG("Exhumed one-to-one chat room 3 with core restart",
exhume_one_to_one_chat_room_3_core_restart,
"LeaksMemory" /*due to core restart*/),
TEST_NO_TAG("Exhumed one-to-one chat room 4", exhume_one_to_one_chat_room_4),
TEST_NO_TAG("New device after group chat room creation", group_chat_room_new_device_after_creation),
TEST_ONE_TAG("Chat room list subscription", group_chat_room_list_subscription, "LeaksMemory"),
TEST_ONE_TAG(
"Complex participant removal scenario", group_chat_room_complex_participant_removal_scenario, "LeaksMemory"),
TEST_NO_TAG("Group chat room subscription denied", group_chat_room_subscription_denied),
TEST_ONE_TAG("Search friend result chat room participants", search_friend_chat_room_participants, "MagicSearch"),
TEST_ONE_TAG("Client loose context of a chatroom", group_chat_loss_of_client_context, "LeaksMemory")};
test_t group_chat3_tests[] = {
TEST_ONE_TAG(
"Participant removed then added", participant_removed_then_added, "LeaksMemory" /*due to core restart*/),
TEST_ONE_TAG("Check if participant device are removed",
group_chat_room_join_one_to_one_chat_room_with_a_new_device_not_notified,
"LeaksMemory" /*due to core restart*/),
TEST_ONE_TAG("Subscribe successful after set chat database path",
subscribe_test_after_set_chat_database_path,
"LeaksMemory" /*due to core restart*/),
TEST_NO_TAG("Send forward message", one_to_one_chat_room_send_forward_message),
TEST_ONE_TAG("Send forward message with restart",
one_to_one_chat_room_send_forward_message_with_restart,
"LeaksMemory" /*due to core restart*/),
TEST_NO_TAG("Send reply message", one_to_one_chat_room_reply_forward_message),
TEST_ONE_TAG("Send reply message with core restart",
one_to_one_chat_room_reply_forward_message_with_restart,
"LeaksMemory" /*due to core restart*/),
TEST_ONE_TAG("Linphone core stop/start and chatroom ref",
core_stop_start_with_chat_room_ref,
"LeaksMemory" /*due to core restart*/),
TEST_ONE_TAG("Subscribe successful after set chat database path",
subscribe_test_after_set_chat_database_path,
"LeaksMemory" /*due to core restart*/),
TEST_NO_TAG("Make sure device unregistration does not triger user to be removed from a group",
group_chat_room_device_unregistered),
TEST_NO_TAG("Admin leaves the room and is reinvited", group_chat_room_admin_creator_leaves_and_is_reinvited),
TEST_NO_TAG("Forward file transfer message", group_chat_forward_file_transfer_message),
TEST_NO_TAG("Forward file transfer message using digest auth on server",
group_chat_forward_file_transfer_message_digest_auth_server),
TEST_NO_TAG("Forward file transfer message using digest auth on server and encrypted FS",
group_chat_forward_file_transfer_message_digest_auth_server_encryptedFS),
};
test_t group_chat4_tests[] = {
TEST_ONE_TAG(
"Reinvited after removed from group chat room 2", group_chat_room_reinvited_after_removed_2, "LeaksMemory"),
TEST_ONE_TAG("Reinvited after removed from group chat room while offline",
group_chat_room_reinvited_after_removed_while_offline,
"LeaksMemory"),
TEST_ONE_TAG("Reinvited after removed from group chat room while offline 2",
group_chat_room_reinvited_after_removed_while_offline_2,
"LeaksMemory"),
910191029103910491059106910791089109911091119112911391149115911691179118911991209121912291239124912591269127912891299130913191329133913491359136913791389139914091419142914391449145914691479148914991509151915291539154915591569157915891599160916191629163916491659166
TEST_NO_TAG("Reinvited after removed from group chat room with several devices",
group_chat_room_reinvited_after_removed_with_several_devices),
TEST_NO_TAG("Notify after disconnection", group_chat_room_notify_after_disconnection),
TEST_ONE_TAG("Notify after core restart",
group_chat_room_notify_after_core_restart,
"LeaksMemory"), /* due to Core restart */
TEST_NO_TAG("Send refer to all participants devices", group_chat_room_send_refer_to_all_devices),
TEST_NO_TAG("Admin add device and doesn't lose admin status", group_chat_room_add_device),
TEST_NO_TAG("Send multiple is composing", multiple_is_composing_notification),
TEST_ONE_TAG("Fallback to basic chat room", group_chat_room_fallback_to_basic_chat_room, "LeaksMemory"),
TEST_NO_TAG("Group chat room creation fails if invited participants don't support it",
group_chat_room_creation_fails_if_invited_participants_dont_support_it),
TEST_NO_TAG("Group chat room creation successful if at least one invited participant supports it",
group_chat_room_creation_successful_if_at_least_one_invited_participant_supports_it),
TEST_ONE_TAG(
"Migrate basic chat room to client group chat room", group_chat_room_migrate_from_basic_chat_room, "Migration"),
TEST_TWO_TAGS("Migrate basic chat room to client group chat room failure",
group_chat_room_migrate_from_basic_to_client_fail,
"LeaksMemory",
"Migration"),
TEST_ONE_TAG("Migrate basic chat room to client group chat room not needed",
group_chat_donot_room_migrate_from_basic_chat_room,
"Migration"),
TEST_NO_TAG("Send file", group_chat_room_send_file),
TEST_NO_TAG("Send file using buffer", group_chat_room_send_file_2)};
test_suite_t group_chat_test_suite = {"Group Chat",
NULL,
NULL,
liblinphone_tester_before_each,
liblinphone_tester_after_each,
sizeof(group_chat_tests) / sizeof(group_chat_tests[0]),
group_chat_tests,
0};
test_suite_t group_chat2_test_suite = {"Group Chat2",
NULL,
NULL,
liblinphone_tester_before_each,
liblinphone_tester_after_each,
sizeof(group_chat2_tests) / sizeof(group_chat2_tests[0]),
group_chat2_tests,
0};
test_suite_t group_chat3_test_suite = {"Group Chat3",
NULL,
NULL,
liblinphone_tester_before_each,
liblinphone_tester_after_each,
sizeof(group_chat3_tests) / sizeof(group_chat3_tests[0]),
group_chat3_tests,
0};
test_suite_t group_chat4_test_suite = {"Group Chat4",
NULL,
NULL,
liblinphone_tester_before_each,
liblinphone_tester_after_each,
sizeof(group_chat4_tests) / sizeof(group_chat4_tests[0]),
group_chat4_tests,
0};
#if __clang__ || ((__GNUC__ == 4 && __GNUC_MINOR__ >= 6) || __GNUC__ > 4)
#pragma GCC diagnostic pop
#endif