Skip to content
GitLab
Projects
Groups
Snippets
Help
Loading...
Help
What's new
10
Help
Support
Community forum
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in
Toggle navigation
Open sidebar
BC
public
belle-sip
Commits
d41ede3e
Commit
d41ede3e
authored
Feb 07, 2014
by
Simon Morlat
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
implement transport timeout for tcp and tls. Default value is set to 63 seconds, as Linux.
parent
f1f6fd7c
Changes
6
Hide whitespace changes
Inline
Side-by-side
Showing
6 changed files
with
107 additions
and
26 deletions
+107
-26
include/belle-sip/sipstack.h
include/belle-sip/sipstack.h
+3
-0
src/sipstack.c
src/sipstack.c
+5
-1
src/transports/stream_channel.c
src/transports/stream_channel.c
+18
-5
src/transports/stream_channel.h
src/transports/stream_channel.h
+1
-1
src/transports/tls_channel_polarssl.c
src/transports/tls_channel_polarssl.c
+33
-16
tester/belle_sip_register_tester.c
tester/belle_sip_register_tester.c
+47
-3
No files found.
include/belle-sip/sipstack.h
View file @
d41ede3e
...
...
@@ -48,6 +48,9 @@ BELLESIP_EXPORT void belle_sip_stack_main(belle_sip_stack_t *stack);
BELLESIP_EXPORT
void
belle_sip_stack_sleep
(
belle_sip_stack_t
*
stack
,
unsigned
int
milliseconds
);
/*the transport timeout is typically the maximum time given for making a connection*/
BELLESIP_EXPORT
void
belle_sip_stack_set_transport_timeout
(
belle_sip_stack_t
*
stack
,
int
timeout_ms
);
BELLESIP_EXPORT
int
belle_sip_stack_get_transport_timeout
(
const
belle_sip_stack_t
*
stack
);
BELLESIP_EXPORT
int
belle_sip_stack_get_dns_timeout
(
const
belle_sip_stack_t
*
stack
);
...
...
src/sipstack.c
View file @
d41ede3e
...
...
@@ -112,7 +112,7 @@ belle_sip_stack_t * belle_sip_stack_new(const char *properties){
stack
->
timer_config
.
T1
=
500
;
stack
->
timer_config
.
T2
=
4000
;
stack
->
timer_config
.
T4
=
5000
;
stack
->
transport_timeout
=
3
0
000
;
stack
->
transport_timeout
=
6
3000
;
stack
->
dns_timeout
=
15000
;
stack
->
dns_srv_enabled
=
TRUE
;
stack
->
inactive_transport_timeout
=
3600
;
/*one hour*/
...
...
@@ -123,6 +123,10 @@ const belle_sip_timer_config_t *belle_sip_stack_get_timer_config(const belle_sip
return
&
stack
->
timer_config
;
}
void
belle_sip_stack_set_transport_timeout
(
belle_sip_stack_t
*
stack
,
int
timeout_ms
){
stack
->
transport_timeout
=
timeout_ms
;
}
int
belle_sip_stack_get_transport_timeout
(
const
belle_sip_stack_t
*
stack
){
return
stack
->
transport_timeout
;
}
...
...
src/transports/stream_channel.c
View file @
d41ede3e
...
...
@@ -141,6 +141,7 @@ int stream_channel_connect(belle_sip_stream_channel_t *obj, const struct addrinf
}
belle_sip_channel_set_socket
((
belle_sip_channel_t
*
)
obj
,
sock
,(
belle_sip_source_func_t
)
stream_channel_process_data
);
belle_sip_source_set_events
((
belle_sip_source_t
*
)
obj
,
BELLE_SIP_EVENT_WRITE
|
BELLE_SIP_EVENT_ERROR
);
belle_sip_source_set_timeout
((
belle_sip_source_t
*
)
obj
,
belle_sip_stack_get_transport_timeout
(
obj
->
base
.
stack
));
belle_sip_main_loop_add_source
(
obj
->
base
.
stack
->
ml
,(
belle_sip_source_t
*
)
obj
);
return
0
;
}
...
...
@@ -164,11 +165,24 @@ BELLE_SIP_INSTANCIATE_CUSTOM_VPTR_BEGIN(belle_sip_stream_channel_t)
}
BELLE_SIP_INSTANCIATE_CUSTOM_VPTR_END
int
finalize_stream_connection
(
belle_sip_stream_channel_t
*
obj
,
struct
sockaddr
*
addr
,
socklen_t
*
slen
)
{
int
finalize_stream_connection
(
belle_sip_stream_channel_t
*
obj
,
unsigned
int
revents
,
struct
sockaddr
*
addr
,
socklen_t
*
slen
)
{
int
err
,
errnum
;
socklen_t
optlen
=
sizeof
(
errnum
);
belle_sip_socket_t
sock
=
belle_sip_source_get_socket
((
belle_sip_source_t
*
)
obj
);
if
(
revents
&
BELLE_SIP_EVENT_READ
){
belle_sip_warning
(
"channel [%p]: getting read event while connecting"
,
obj
);
return
-
1
;
}
if
(
revents
==
BELLE_SIP_EVENT_TIMEOUT
){
belle_sip_warning
(
"channel [%p]: user-defined transport timeout."
,
obj
);
return
-
1
;
}
if
(
!
(
revents
&
BELLE_SIP_EVENT_WRITE
)){
belle_sip_warning
(
"channel [%p]: getting unexpected event while connecting"
,
obj
);
return
-
1
;
}
err
=
getsockopt
(
sock
,
SOL_SOCKET
,
SO_ERROR
,(
void
*
)
&
errnum
,
&
optlen
);
if
(
err
!=
0
){
belle_sip_error
(
"Failed to retrieve connection status for fd [%i]: cause [%s]"
,
sock
,
belle_sip_get_socket_error_string
());
...
...
@@ -203,17 +217,16 @@ static int stream_channel_process_data(belle_sip_stream_channel_t *obj,unsigned
belle_sip_message
(
"TCP channel process_data"
);
if
(
state
==
BELLE_SIP_CHANNEL_CONNECTING
&&
(
revents
&
BELLE_SIP_EVENT_WRITE
))
{
if
(
finalize_stream_connection
(
obj
,(
struct
sockaddr
*
)
&
ss
,
&
addrlen
))
{
if
(
state
==
BELLE_SIP_CHANNEL_CONNECTING
)
{
if
(
finalize_stream_connection
(
obj
,
revents
,(
struct
sockaddr
*
)
&
ss
,
&
addrlen
))
{
belle_sip_error
(
"Cannot connect to [%s://%s:%i]"
,
belle_sip_channel_get_transport_name
(
base
),
base
->
peer_name
,
base
->
peer_port
);
channel_set_state
(
base
,
BELLE_SIP_CHANNEL_ERROR
);
return
BELLE_SIP_STOP
;
}
belle_sip_source_set_events
((
belle_sip_source_t
*
)
obj
,
BELLE_SIP_EVENT_READ
|
BELLE_SIP_EVENT_ERROR
);
belle_sip_source_set_timeout
((
belle_sip_source_t
*
)
obj
,
-
1
);
belle_sip_channel_set_ready
(
base
,(
struct
sockaddr
*
)
&
ss
,
addrlen
);
return
BELLE_SIP_CONTINUE
;
}
else
if
(
state
==
BELLE_SIP_CHANNEL_READY
)
{
return
belle_sip_channel_process_data
(
base
,
revents
);
}
else
{
...
...
src/transports/stream_channel.h
View file @
d41ede3e
...
...
@@ -49,7 +49,7 @@ belle_sip_channel_t * belle_sip_stream_channel_new_child(belle_sip_stack_t *stac
void
stream_channel_close
(
belle_sip_stream_channel_t
*
obj
);
int
stream_channel_connect
(
belle_sip_stream_channel_t
*
obj
,
const
struct
addrinfo
*
ai
);
/*return 0 if succeed*/
int
finalize_stream_connection
(
belle_sip_stream_channel_t
*
obj
,
struct
sockaddr
*
addr
,
socklen_t
*
slen
);
int
finalize_stream_connection
(
belle_sip_stream_channel_t
*
obj
,
unsigned
int
revents
,
struct
sockaddr
*
addr
,
socklen_t
*
slen
);
int
stream_channel_send
(
belle_sip_stream_channel_t
*
obj
,
const
void
*
buf
,
size_t
buflen
);
int
stream_channel_recv
(
belle_sip_stream_channel_t
*
obj
,
void
*
buf
,
size_t
buflen
);
...
...
src/transports/tls_channel_polarssl.c
View file @
d41ede3e
...
...
@@ -180,33 +180,50 @@ static int tls_channel_handshake(belle_sip_tls_channel_t *channel) {
}
return
ret
;
}
static
int
tls_process_handshake
(
belle_sip_channel_t
*
obj
){
belle_sip_tls_channel_t
*
channel
=
(
belle_sip_tls_channel_t
*
)
obj
;
int
err
=
tls_channel_handshake
(
channel
);
if
(
err
==
0
){
belle_sip_message
(
"Channel [%p]: SSL handshake finished."
,
obj
);
belle_sip_source_set_timeout
((
belle_sip_source_t
*
)
obj
,
-
1
);
belle_sip_channel_set_ready
(
obj
,(
struct
sockaddr
*
)
&
channel
->
ss
,
channel
->
socklen
);
}
else
if
(
err
==
POLARSSL_ERR_NET_WANT_READ
||
err
==
POLARSSL_ERR_NET_WANT_WRITE
){
belle_sip_message
(
"Channel [%p]: SSL handshake in progress..."
,
obj
);
}
else
{
char
tmp
[
128
];
error_strerror
(
err
,
tmp
,
sizeof
(
tmp
));
belle_sip_error
(
"Channel [%p]: SSL handshake failed : %s"
,
obj
,
tmp
);
return
-
1
;
}
return
0
;
}
static
int
tls_process_data
(
belle_sip_channel_t
*
obj
,
unsigned
int
revents
){
belle_sip_tls_channel_t
*
channel
=
(
belle_sip_tls_channel_t
*
)
obj
;
int
err
;
if
(
obj
->
state
==
BELLE_SIP_CHANNEL_CONNECTING
)
{
if
(
!
channel
->
socket_connected
&&
(
revents
&
BELLE_SIP_EVENT_WRITE
)
)
{
if
(
!
channel
->
socket_connected
)
{
channel
->
socklen
=
sizeof
(
channel
->
ss
);
if
(
finalize_stream_connection
((
belle_sip_stream_channel_t
*
)
obj
,(
struct
sockaddr
*
)
&
channel
->
ss
,
&
channel
->
socklen
))
{
if
(
finalize_stream_connection
((
belle_sip_stream_channel_t
*
)
obj
,
revents
,
(
struct
sockaddr
*
)
&
channel
->
ss
,
&
channel
->
socklen
))
{
goto
process_error
;
}
belle_sip_source_set_events
((
belle_sip_source_t
*
)
channel
,
BELLE_SIP_EVENT_READ
|
BELLE_SIP_EVENT_ERROR
);
channel
->
socket_connected
=
1
;
belle_sip_message
(
"Channel [%p]: Connected at TCP level, now doing TLS handshake"
,
obj
);
}
err
=
tls_channel_handshake
(
channel
)
/*ssl_handshake(&channel->sslctx)*/
;
if
(
err
==
0
){
belle_sip_message
(
"Channel [%p]: SSL handshake finished."
,
obj
);
belle_sip_channel_set_ready
(
obj
,(
struct
sockaddr
*
)
&
channel
->
ss
,
channel
->
socklen
);
}
else
if
(
err
==
POLARSSL_ERR_NET_WANT_READ
||
err
==
POLARSSL_ERR_NET_WANT_WRITE
){
belle_sip_message
(
"Channel [%p]: SSL handshake in progress..."
,
obj
);
channel
->
socket_connected
=
1
;
belle_sip_source_set_events
((
belle_sip_source_t
*
)
channel
,
BELLE_SIP_EVENT_READ
|
BELLE_SIP_EVENT_ERROR
);
belle_sip_source_set_timeout
((
belle_sip_source_t
*
)
obj
,
belle_sip_stack_get_transport_timeout
(
obj
->
stack
));
if
(
tls_process_handshake
(
obj
)
==-
1
)
goto
process_error
;
}
else
{
char
tmp
[
128
];
error_strerror
(
err
,
tmp
,
sizeof
(
tmp
));
belle_sip_error
(
"Channel [%p]: SSL handshake failed : %s"
,
obj
,
tmp
);
goto
process_error
;
if
(
revents
&
BELLE_SIP_EVENT_READ
){
if
(
tls_process_handshake
(
obj
)
==-
1
)
goto
process_error
;
}
else
if
(
revents
==
BELLE_SIP_EVENT_TIMEOUT
){
belle_sip_error
(
"channel [%p]: SSL handshake took too much time."
,
obj
);
goto
process_error
;
}
else
{
belle_sip_warning
(
"channel [%p]: unexpected event [%i] during TLS handshake."
,
obj
,
revents
);
}
}
}
else
if
(
obj
->
state
==
BELLE_SIP_CHANNEL_READY
)
{
return
belle_sip_channel_process_data
(
obj
,
revents
);
}
else
{
...
...
tester/belle_sip_register_tester.c
View file @
d41ede3e
...
...
@@ -29,10 +29,15 @@ const char *test_domain="test.linphone.org";
const
char
*
auth_domain
=
"sip.linphone.org"
;
const
char
*
client_auth_domain
=
"client.example.org"
;
const
char
*
client_auth_outbound_proxy
=
"sips:sip2.linphone.org:5063"
;
const
char
*
no_server_running_here
=
"sip:test.linphone.org:3;transport=tcp"
;
const
char
*
no_response_here
=
"sip:78.220.48.77:3;transport=tcp"
;
const
char
*
test_domain_tls_to_tcp
=
"sip:test.linphone.org:5060;transport=tls"
;
static
int
is_register_ok
;
static
int
number_of_challenge
;
static
int
using_transaction
;
static
int
io_error_count
=
0
;
belle_sip_stack_t
*
stack
;
belle_sip_provider_t
*
prov
;
static
belle_sip_listener_t
*
l
;
...
...
@@ -50,8 +55,9 @@ static void process_dialog_terminated(void *user_ctx, const belle_sip_dialog_ter
static
void
process_io_error
(
void
*
user_ctx
,
const
belle_sip_io_error_event_t
*
event
){
BELLESIP_UNUSED
(
user_ctx
);
BELLESIP_UNUSED
(
event
);
belle_sip_message
(
"process_io_error"
);
belle_sip_message
(
"process_io_error
, exiting main loop
"
);
belle_sip_main_loop_quit
(
belle_sip_stack_get_main_loop
(
stack
));
io_error_count
++
;
/*CU_ASSERT(CU_FALSE);*/
}
...
...
@@ -278,6 +284,7 @@ belle_sip_request_t* try_register_user_at_domain(belle_sip_stack_t * stack
belle_sip_header_via_new
(),
70
);
is_register_ok
=
0
;
io_error_count
=
0
;
using_transaction
=
0
;
belle_sip_message_add_header
(
BELLE_SIP_MESSAGE
(
req
),
BELLE_SIP_HEADER
(
belle_sip_header_expires_create
(
600
)));
belle_sip_message_add_header
(
BELLE_SIP_MESSAGE
(
req
),
BELLE_SIP_HEADER
(
belle_sip_header_contact_new
()));
...
...
@@ -287,7 +294,7 @@ belle_sip_request_t* try_register_user_at_domain(belle_sip_stack_t * stack
belle_sip_client_transaction_t
*
t
=
belle_sip_provider_create_client_transaction
(
prov
,
req
);
belle_sip_client_transaction_send_request_to
(
t
,
outbound
?
belle_sip_uri_parse
(
outbound
)
:
NULL
);
}
else
belle_sip_provider_send_request
(
prov
,
req
);
for
(
i
=
0
;
!
is_register_ok
&&
i
<
2
;
i
++
)
for
(
i
=
0
;
!
is_register_ok
&&
i
<
2
&&
io_error_count
==
0
;
i
++
)
belle_sip_stack_sleep
(
stack
,
5000
);
CU_ASSERT_EQUAL
(
is_register_ok
,
success_expected
);
if
(
success_expected
)
CU_ASSERT_EQUAL
(
using_transaction
,
use_transaction
);
...
...
@@ -400,6 +407,7 @@ static void test_bad_request(void) {
belle_sip_header_route_t
*
route
;
belle_sip_header_to_t
*
to
=
belle_sip_header_to_create2
(
"sip:toto@titi.com"
,
NULL
);
belle_sip_listener_callbacks_t
cbs
;
belle_sip_listening_point_t
*
lp
=
belle_sip_provider_get_listening_point
(
prov
,
"TCP"
);
int
bad_request_response_received
=
0
;
memset
(
&
cbs
,
0
,
sizeof
(
cbs
));
...
...
@@ -432,6 +440,8 @@ static void test_bad_request(void) {
CU_ASSERT_TRUE
(
bad_request_response_received
==
1
);
belle_sip_provider_remove_sip_listener
(
prov
,
bad_req_listener
);
belle_sip_object_unref
(
bad_req_listener
);
belle_sip_listening_point_clean_channels
(
lp
);
}
static
void
test_register_authenticate
(
void
)
{
...
...
@@ -475,6 +485,37 @@ static void test_register_client_authenticated(void) {
if
(
reg
)
belle_sip_object_unref
(
reg
);
}
static
void
test_connection_failure
(
void
){
belle_sip_request_t
*
req
;
io_error_count
=
0
;
req
=
try_register_user_at_domain
(
stack
,
prov
,
"TCP"
,
1
,
"tester"
,
"sip.linphone.org"
,
no_server_running_here
,
0
);
CU_ASSERT_TRUE
(
io_error_count
>=
1
);
if
(
req
)
belle_sip_object_unref
(
req
);
}
static
void
test_connection_too_long
(
void
){
belle_sip_request_t
*
req
;
io_error_count
=
0
;
int
orig
=
belle_sip_stack_get_transport_timeout
(
stack
);
belle_sip_stack_set_transport_timeout
(
stack
,
2000
);
req
=
try_register_user_at_domain
(
stack
,
prov
,
"TCP"
,
1
,
"tester"
,
"sip.linphone.org"
,
no_response_here
,
0
);
CU_ASSERT_TRUE
(
io_error_count
>=
1
);
belle_sip_stack_set_transport_timeout
(
stack
,
orig
);
if
(
req
)
belle_sip_object_unref
(
req
);
}
static
void
test_tls_to_tcp
(
void
){
io_error_count
=
0
;
belle_sip_request_t
*
req
;
int
orig
=
belle_sip_stack_get_transport_timeout
(
stack
);
belle_sip_stack_set_transport_timeout
(
stack
,
2000
);
req
=
try_register_user_at_domain
(
stack
,
prov
,
"TLS"
,
1
,
"tester"
,
test_domain
,
test_domain_tls_to_tcp
,
0
);
if
(
req
){
CU_ASSERT_TRUE
(
io_error_count
>=
1
);
belle_sip_object_unref
(
req
);
}
belle_sip_stack_set_transport_timeout
(
stack
,
orig
);
}
test_t
register_tests
[]
=
{
{
"Stateful UDP"
,
stateful_register_udp
},
...
...
@@ -490,7 +531,10 @@ test_t register_tests[] = {
{
"Bad TCP request"
,
test_bad_request
},
{
"Authenticate"
,
test_register_authenticate
},
{
"TLS client cert authentication"
,
test_register_client_authenticated
},
{
"Channel inactive"
,
test_register_channel_inactive
}
{
"Channel inactive"
,
test_register_channel_inactive
},
{
"TCP connection failure"
,
test_connection_failure
},
{
"TCP connection too long"
,
test_connection_too_long
},
{
"TLS connection to TCP server"
,
test_tls_to_tcp
}
};
test_suite_t
register_test_suite
=
{
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
.
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment