Commit 123b4209 authored by Simon Morlat's avatar Simon Morlat

fix crash when a channel encouters an error and is immediately cleaned by...

fix crash when a channel encouters an error and is immediately cleaned by listening point AND the transaction is still ref'd somewhere else.
parent 4da1c5ea
......@@ -144,8 +144,11 @@ static void on_channel_state_changed(belle_sip_channel_listener_t *l, belle_sip_
} else {
belle_sip_transaction_terminate(t);
}
belle_sip_object_unref(((belle_sip_transaction_t*)t)->channel);
((belle_sip_transaction_t*)t)->channel = NULL;
if (t->channel){
belle_sip_channel_remove_listener(t->channel, l);
belle_sip_object_unref(t->channel);
t->channel = NULL;
}
belle_sip_object_unref(t);
break;
......
......@@ -567,6 +567,7 @@ static void test_bad_request(void) {
belle_sip_listening_point_clean_channels(lp);
}
static void test_register_authenticate(void) {
belle_sip_request_t *reg;
number_of_challenge=0;
......@@ -599,6 +600,44 @@ static void test_register_channel_inactive(void){
}
}
static void test_channel_moving_to_error_and_cleaned(void){
belle_sip_listening_point_t *lp=belle_sip_provider_get_listening_point(prov,"UDP");
BC_ASSERT_PTR_NOT_NULL(lp);
if (lp) {
belle_sip_request_t *req;
belle_sip_client_transaction_t *tr;
char identity[128];
char uri[128];
belle_sip_listening_point_clean_channels(lp);
BC_ASSERT_EQUAL(belle_sip_listening_point_get_channel_count(lp),0,int,"%d");
snprintf(identity,sizeof(identity),"Tester <sip:%s@%s>","bellesip",test_domain);
snprintf(uri,sizeof(uri),"sip:%s",test_domain);
req = belle_sip_request_create(
belle_sip_uri_parse(uri),
"REGISTER",
belle_sip_provider_create_call_id(prov),
belle_sip_header_cseq_create(20,"REGISTER"),
belle_sip_header_from_create2(identity,BELLE_SIP_RANDOM_TAG),
belle_sip_header_to_create2(identity,NULL),
belle_sip_header_via_new(),
70);
tr = belle_sip_provider_create_client_transaction(prov, req);
belle_sip_client_transaction_send_request(tr);
belle_sip_object_ref(tr);
BC_ASSERT_EQUAL(belle_sip_listening_point_get_channel_count(lp),1,int,"%d");
/*calling notify_server_error() will make the channel enter the error state, which is what we want to test*/
belle_sip_channel_notify_server_error((belle_sip_channel_t*)lp->channels->data);
/*immediately after, we clean the channel from the listening point*/
belle_sip_listening_point_clean_channels(lp);
/*we just want to verify that it doesn't crash*/
belle_sip_stack_sleep(stack, 1000);
belle_sip_object_unref(tr);
}
}
static void test_register_client_authenticated(void) {
......@@ -853,6 +892,7 @@ test_t register_tests[] = {
TEST_NO_TAG("Authenticate", test_register_authenticate),
TEST_NO_TAG("TLS client cert authentication", test_register_client_authenticated),
TEST_NO_TAG("Channel inactive", test_register_channel_inactive),
TEST_NO_TAG("Channel moving to error test and cleaned", test_channel_moving_to_error_and_cleaned),
TEST_NO_TAG("TCP connection failure", test_connection_failure),
TEST_NO_TAG("TCP connection too long", test_connection_too_long_tcp),
TEST_NO_TAG("TLS connection too long", test_connection_too_long_tls),
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment