diff --git a/coreapi/conference.cc b/coreapi/conference.cc index d917d7e01..df8a6c92f 100644 --- a/coreapi/conference.cc +++ b/coreapi/conference.cc @@ -562,7 +562,7 @@ RemoteConference::RemoteConference(LinphoneCore *core): m_vtable->call_state_changed = callStateChangedCb; m_vtable->transfer_state_changed = transferStateChanged; linphone_core_v_table_set_user_data(m_vtable, this); - linphone_core_add_listener(m_core, m_vtable); + _linphone_core_add_listener(m_core, m_vtable, FALSE, TRUE); } RemoteConference::~RemoteConference() { @@ -609,7 +609,7 @@ int RemoteConference::addParticipant(LinphoneCall *call) { int RemoteConference::removeParticipant(const LinphoneAddress *uri) { SalOp *op; const char *from; - LinphoneAddress *refer_to; + char *tmp, *refer_to; int res; switch(m_state) { @@ -620,10 +620,11 @@ int RemoteConference::removeParticipant(const LinphoneAddress *uri) { sal_op_set_from(op, from); sal_op_set_to(op, m_focusContact); - refer_to = linphone_address_clone(uri); - linphone_address_set_header(refer_to, "method", "BYE"); - res = sal_call_refer(op, linphone_address_as_string(refer_to)); - linphone_address_unref(refer_to); + tmp = linphone_address_as_string_uri_only(uri); + refer_to = ms_strdup_printf("%s;method=BYE", tmp); + res = sal_call_refer(op, refer_to); + ms_free(tmp); + ms_free(refer_to); if(res == 0) return Conference::removeParticipant(uri); else return -1; diff --git a/coreapi/linphonecore.c b/coreapi/linphonecore.c index 880271658..a81293963 100644 --- a/coreapi/linphonecore.c +++ b/coreapi/linphonecore.c @@ -1675,7 +1675,7 @@ static void linphone_core_init(LinphoneCore * lc, const LinphoneCoreVTable *vtab linphone_task_list_init(&lc->hooks); memcpy(local_vtable,vtable,sizeof(LinphoneCoreVTable)); - _linphone_core_add_listener(lc, local_vtable, TRUE); + _linphone_core_add_listener(lc, local_vtable, TRUE, TRUE); linphone_core_set_state(lc,LinphoneGlobalStartup,"Starting up"); ortp_init(); diff --git a/coreapi/linphonecore_jni.cc b/coreapi/linphonecore_jni.cc index 433efcae4..f6361e389 100644 --- a/coreapi/linphonecore_jni.cc +++ b/coreapi/linphonecore_jni.cc @@ -1217,7 +1217,7 @@ extern "C" void Java_org_linphone_core_LinphoneCoreImpl_removeListener(JNIEnv* e VTableReference *ref=(VTableReference*)(iterator->data); LinphoneCoreVTable *vTable = ref->valid ? ref->vtable : NULL; iterator = iterator->next; //Because linphone_core_remove_listener may change the list - if (vTable) { + if (vTable && !ref->internal) { LinphoneCoreData *data = (LinphoneCoreData*) linphone_core_v_table_get_user_data(vTable); if (data && env->IsSameObject(data->listener, jlistener)) { linphone_core_remove_listener(core, vTable); diff --git a/coreapi/private.h b/coreapi/private.h index 23fcbd760..57a924cc8 100644 --- a/coreapi/private.h +++ b/coreapi/private.h @@ -1356,13 +1356,14 @@ struct _VTableReference{ LinphoneCoreVTable *vtable; bool_t valid; bool_t autorelease; + bool_t internal; }; typedef struct _VTableReference VTableReference; void v_table_reference_destroy(VTableReference *ref); -void _linphone_core_add_listener(LinphoneCore *lc, LinphoneCoreVTable *vtable, bool_t autorelease); +void _linphone_core_add_listener(LinphoneCore *lc, LinphoneCoreVTable *vtable, bool_t autorelease, bool_t internal); #ifdef VIDEO_ENABLED LINPHONE_PUBLIC MSWebCam *linphone_call_get_video_device(const LinphoneCall *call); MSWebCam *get_nowebcam_device(void); diff --git a/coreapi/vtables.c b/coreapi/vtables.c index b01a91f08..226f46be0 100644 --- a/coreapi/vtables.c +++ b/coreapi/vtables.c @@ -253,10 +253,11 @@ void linphone_core_notify_log_collection_upload_progress_indication(LinphoneCore cleanup_dead_vtable_refs(lc); } -static VTableReference * v_table_reference_new(LinphoneCoreVTable *vtable, bool_t autorelease){ +static VTableReference * v_table_reference_new(LinphoneCoreVTable *vtable, bool_t autorelease, bool_t internal){ VTableReference *ref=ms_new0(VTableReference,1); ref->valid=1; ref->autorelease=autorelease; + ref->internal = internal; ref->vtable=vtable; return ref; } @@ -266,13 +267,13 @@ void v_table_reference_destroy(VTableReference *ref){ ms_free(ref); } -void _linphone_core_add_listener(LinphoneCore *lc, LinphoneCoreVTable *vtable, bool_t autorelease) { +void _linphone_core_add_listener(LinphoneCore *lc, LinphoneCoreVTable *vtable, bool_t autorelease, bool_t internal) { ms_message("Vtable [%p] registered on core [%p]",lc,vtable); - lc->vtable_refs=ms_list_append(lc->vtable_refs,v_table_reference_new(vtable, autorelease)); + lc->vtable_refs=ms_list_append(lc->vtable_refs,v_table_reference_new(vtable, autorelease, internal)); } void linphone_core_add_listener(LinphoneCore *lc, LinphoneCoreVTable *vtable){ - _linphone_core_add_listener(lc, vtable, FALSE); + _linphone_core_add_listener(lc, vtable, FALSE, FALSE); } void linphone_core_remove_listener(LinphoneCore *lc, const LinphoneCoreVTable *vtable) { diff --git a/gtk/main.c b/gtk/main.c index 7dc818271..8dd0f8453 100644 --- a/gtk/main.c +++ b/gtk/main.c @@ -823,7 +823,7 @@ static void linphone_gtk_update_call_buttons(LinphoneCall *call){ conf_frame=(GtkWidget *)g_object_get_data(G_OBJECT(mw),"conf_frame"); if(conf_frame==NULL){ linphone_gtk_enable_transfer_button(lc,call_list_size>1); - linphone_gtk_enable_conference_button(lc,call_list_size>1); + linphone_gtk_enable_conference_button(lc,call_list_size>0); } else { linphone_gtk_enable_transfer_button(lc,FALSE); linphone_gtk_enable_conference_button(lc,FALSE); diff --git a/tester/multi_call_tester.c b/tester/multi_call_tester.c index 8ded2285d..a8747ba62 100644 --- a/tester/multi_call_tester.c +++ b/tester/multi_call_tester.c @@ -602,6 +602,7 @@ static void eject_from_3_participants_conference(LinphoneCoreManager *marie, Lin else { BC_ASSERT_TRUE(wait_for_list(lcs,&marie->stat.number_of_LinphoneTransferCallConnected,initial_marie_stat.number_of_LinphoneTransferCallConnected+1,5000)); BC_ASSERT_TRUE(wait_for_list(lcs,&marie->stat.number_of_LinphoneCallEnd,initial_marie_stat.number_of_LinphoneCallEnd+1,5000)); + BC_ASSERT_TRUE(wait_for_list(lcs,&laure->stat.number_of_LinphoneCallEnd,initial_laure_stat.number_of_LinphoneCallEnd+1,5000)); } BC_ASSERT_PTR_NOT_NULL(linphone_core_get_conference(marie->lc)); @@ -612,6 +613,7 @@ static void eject_from_3_participants_conference(LinphoneCoreManager *marie, Lin else { BC_ASSERT_TRUE(wait_for_list(lcs,&marie->stat.number_of_LinphoneTransferCallConnected,initial_marie_stat.number_of_LinphoneTransferCallConnected+2,5000)); BC_ASSERT_TRUE(wait_for_list(lcs,&marie->stat.number_of_LinphoneCallEnd,initial_marie_stat.number_of_LinphoneCallEnd+2,5000)); + BC_ASSERT_TRUE(wait_for_list(lcs,&pauline->stat.number_of_LinphoneCallEnd,initial_pauline_stat.number_of_LinphoneCallEnd+1,5000)); } BC_ASSERT_TRUE(wait_for_list(lcs,&pauline->stat.number_of_LinphoneCallStreamsRunning,initial_pauline_stat.number_of_LinphoneCallStreamsRunning+1,5000)); @@ -639,7 +641,7 @@ static void eject_from_3_participants_conference(LinphoneCoreManager *marie, Lin BC_ASSERT_PTR_NOT_NULL(linphone_core_get_current_call(pauline->lc)); BC_ASSERT_PTR_NOT_NULL(linphone_core_get_current_call(laure->lc)); } else { - BC_ASSERT_TRUE(wait_for_list(lcs,&pauline->stat.number_of_LinphoneCallEnd,initial_pauline_stat.number_of_LinphoneCallEnd+1,5000)); + BC_ASSERT_TRUE(wait_for_list(lcs,&pauline->stat.number_of_LinphoneCallEnd,initial_pauline_stat.number_of_LinphoneCallEnd+2,5000)); } if(!is_remote_conf) {