Skip to content
GitLab
Menu
Projects
Groups
Snippets
Loading...
Help
Help
Support
Community forum
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in
Toggle navigation
Menu
Open sidebar
BC
public
mediastreamer2
Commits
abf2a7ec
Commit
abf2a7ec
authored
Apr 09, 2013
by
Simon Morlat
Browse files
factorize code related to call quality indicator.
add accessors to loss and late rates.
parent
d9ce543d
Changes
8
Hide whitespace changes
Inline
Side-by-side
Showing
8 changed files
with
121 additions
and
46 deletions
+121
-46
include/mediastreamer2/mediastream.h
include/mediastreamer2/mediastream.h
+12
-4
include/mediastreamer2/qualityindicator.h
include/mediastreamer2/qualityindicator.h
+43
-9
src/voip/audiostream.c
src/voip/audiostream.c
+10
-25
src/voip/mediastream.c
src/voip/mediastream.c
+35
-1
src/voip/private.h
src/voip/private.h
+1
-1
src/voip/qualityindicator.c
src/voip/qualityindicator.c
+12
-2
src/voip/videostream.c
src/voip/videostream.c
+6
-2
tools/mediastream.c
tools/mediastream.c
+2
-2
No files found.
include/mediastreamer2/mediastream.h
View file @
abf2a7ec
...
...
@@ -86,10 +86,15 @@ struct _MediaStream {
MSFilter
*
decoder
;
MSFilter
*
voidsink
;
MSBitrateController
*
rc
;
MSQualityIndicator
*
qi
;
IceCheckList
*
ice_check_list
;
OrtpZrtpContext
*
zrtp_context
;
srtp_t
srtp_session
;
time_t
start_time
;
time_t
last_iterate_time
;
bool_t
use_rc
;
bool_t
is_beginning
;
bool_t
pad
[
2
];
};
typedef
struct
_MediaStream
MediaStream
;
...
...
@@ -106,7 +111,14 @@ MS2_PUBLIC void media_stream_enable_adaptive_jittcomp(MediaStream *stream, bool_
MS2_PUBLIC
bool_t
media_stream_enable_srtp
(
MediaStream
*
stream
,
enum
ortp_srtp_crypto_suite_t
suite
,
const
char
*
snd_key
,
const
char
*
rcv_key
);
MS2_PUBLIC
const
MSQualityIndicator
*
media_stream_get_quality_indicator
(
MediaStream
*
stream
);
MS2_PUBLIC
float
media_stream_get_quality_rating
(
MediaStream
*
stream
);
MS2_PUBLIC
float
media_stream_get_average_quality_rating
(
MediaStream
*
stream
);
/*shall only called internally*/
void
media_stream_iterate
(
MediaStream
*
stream
);
/**
* @addtogroup audio_stream_api
* @{
...
...
@@ -140,16 +152,12 @@ struct _AudioStream
uint64_t
last_packet_count
;
time_t
last_packet_time
;
EchoLimiterType
el_type
;
/*use echo limiter: two MSVolume, measured input level controlling local output level*/
MSQualityIndicator
*
qi
;
time_t
start_time
;
time_t
last_iterate_time
;
uint32_t
features
;
bool_t
play_dtmfs
;
bool_t
use_gc
;
bool_t
use_agc
;
bool_t
eq_active
;
bool_t
use_ng
;
/*noise gate*/
bool_t
is_beginning
;
bool_t
is_ec_delay_set
;
};
...
...
include/mediastreamer2/qualityindicator.h
View file @
abf2a7ec
...
...
@@ -30,17 +30,51 @@ typedef struct _MSQualityIndicator MSQualityIndicator;
extern
"C"
{
#endif
MSQualityIndicator
*
ms_quality_indicator_new
(
RtpSession
*
session
);
/**
* Creates a quality indicator object.
* @param session the RtpSession being monitored.
**/
MS2_PUBLIC
MSQualityIndicator
*
ms_quality_indicator_new
(
RtpSession
*
session
);
/**
* Updates quality indicator based on a received RTCP packet.
**/
MS2_PUBLIC
void
ms_quality_indicator_update_from_feedback
(
MSQualityIndicator
*
qi
,
mblk_t
*
rtcp
);
/**
* Updates quality indicator based on the local statistics directly computed by the RtpSession used when creating the indicator.
* This function must be called typically every second.
**/
MS2_PUBLIC
void
ms_quality_indicator_update_local
(
MSQualityIndicator
*
qi
);
/**
* Return the real time rating of the session. Its value is between 0 (worse) and 5.0 (best).
**/
MS2_PUBLIC
float
ms_quality_indicator_get_rating
(
MSQualityIndicator
*
qi
);
/**
* Returns the average rating of the session, that is the rating for all the duration of the session.
**/
MS2_PUBLIC
float
ms_quality_indicator_get_average_rating
(
MSQualityIndicator
*
qi
);
/**
* Returns the local loss rate, as computed internally by ms_quality_indicator_update_local().
* This method is for advanced usage.
**/
MS2_PUBLIC
float
ms_quality_indicator_get_local_loss_rate
(
const
MSQualityIndicator
*
qi
);
/**
* Returns the local late rate, as computed internally by ms_quality_indicator_update_local().
* This method is for advanced usage.
**/
MS2_PUBLIC
float
ms_quality_indicator_get_local_late_rate
(
const
MSQualityIndicator
*
qi
);
/**
* Destroys the quality indicator object.
**/
MS2_PUBLIC
void
ms_quality_indicator_destroy
(
MSQualityIndicator
*
qi
);
float
ms_quality_indicator_get_rating
(
MSQualityIndicator
*
qi
);
float
ms_quality_indicator_get_average_rating
(
MSQualityIndicator
*
qi
);
void
ms_quality_indicator_update_from_feedback
(
MSQualityIndicator
*
qi
,
mblk_t
*
rtcp
);
void
ms_quality_indicator_update_local
(
MSQualityIndicator
*
qi
);
void
ms_quality_indicator_destroy
(
MSQualityIndicator
*
qi
);
#ifdef __cplusplus
}
...
...
src/voip/audiostream.c
View file @
abf2a7ec
...
...
@@ -63,7 +63,6 @@ static void audio_stream_free(AudioStream *stream) {
if
(
stream
->
recorder
)
ms_filter_destroy
(
stream
->
recorder
);
if
(
stream
->
recorder_mixer
)
ms_filter_destroy
(
stream
->
recorder_mixer
);
if
(
stream
->
recorder_file
)
ms_free
(
stream
->
recorder_file
);
if
(
stream
->
qi
)
ms_quality_indicator_destroy
(
stream
->
qi
);
ms_free
(
stream
);
}
...
...
@@ -122,17 +121,12 @@ static void audio_stream_process_rtcp(AudioStream *stream, mblk_t *m){
ms_message
(
"audio_stream_iterate(): remote statistics available
\n\t
remote's interarrival jitter=%u
\n
"
"
\t
remote's lost packets percentage since last report=%f
\n\t
round trip time=%f seconds"
,
ij
,
flost
,
rt
);
if
(
stream
->
ms
.
rc
)
ms_bitrate_controller_process_rtcp
(
stream
->
ms
.
rc
,
m
);
if
(
stream
->
qi
)
ms_quality_indicator_update_from_feedback
(
stream
->
qi
,
m
);
if
(
stream
->
ms
.
qi
)
ms_quality_indicator_update_from_feedback
(
stream
->
ms
.
qi
,
m
);
}
}
while
(
rtcp_next_packet
(
m
));
}
void
audio_stream_iterate
(
AudioStream
*
stream
){
time_t
curtime
=
time
(
NULL
);
if
(
stream
->
is_beginning
&&
ms_time
(
NULL
)
-
stream
->
start_time
>
15
){
rtp_session_set_rtcp_report_interval
(
stream
->
ms
.
session
,
5000
);
stream
->
is_beginning
=
FALSE
;
}
if
(
stream
->
ms
.
evq
){
OrtpEvent
*
ev
=
ortp_ev_queue_get
(
stream
->
ms
.
evq
);
if
(
ev
!=
NULL
){
...
...
@@ -148,10 +142,7 @@ void audio_stream_iterate(AudioStream *stream){
ortp_event_destroy
(
ev
);
}
}
if
(
stream
->
ms
.
ice_check_list
)
ice_check_list_process
(
stream
->
ms
.
ice_check_list
,
stream
->
ms
.
session
);
/*we choose to update the quality indicator as much as possible, since local statistics can be computed realtime. */
if
(
stream
->
qi
&&
curtime
>
stream
->
last_iterate_time
)
ms_quality_indicator_update_local
(
stream
->
qi
);
stream
->
last_iterate_time
=
curtime
;
media_stream_iterate
(
&
stream
->
ms
);
}
bool_t
audio_stream_alive
(
AudioStream
*
stream
,
int
timeout
){
...
...
@@ -191,7 +182,7 @@ static void stop_preload_graph(AudioStream *stream){
}
bool_t
audio_stream_started
(
AudioStream
*
stream
){
return
stream
->
start_time
!=
0
;
return
stream
->
ms
.
start_time
!=
0
;
}
/* This function is used either on IOS to workaround the long time to initialize the Audio Unit or for ICE candidates gathering. */
...
...
@@ -261,7 +252,7 @@ int audio_stream_start_full(AudioStream *stream, RtpProfile *profile, const char
else
stream
->
dtmfgen
=
NULL
;
rtp_session_signal_connect
(
rtps
,
"telephone-event"
,(
RtpCallback
)
on_dtmf_received
,(
unsigned
long
)
stream
);
rtp_session_signal_connect
(
rtps
,
"payload_type_changed"
,(
RtpCallback
)
payload_type_changed
,(
unsigned
long
)
&
stream
->
ms
);
rtp_session_signal_connect
(
rtps
,
"payload_type_changed"
,(
RtpCallback
)
mediastream_
payload_type_changed
,(
unsigned
long
)
&
stream
->
ms
);
/* creates the local part */
if
(
captcard
!=
NULL
){
if
(
stream
->
soundread
==
NULL
)
...
...
@@ -440,7 +431,6 @@ int audio_stream_start_full(AudioStream *stream, RtpProfile *profile, const char
if
(
stream
->
ms
.
use_rc
){
stream
->
ms
.
rc
=
ms_audio_bitrate_controller_new
(
stream
->
ms
.
session
,
stream
->
ms
.
encoder
,
0
);
}
stream
->
qi
=
ms_quality_indicator_new
(
stream
->
ms
.
session
);
/* Create PLC */
if
((
stream
->
features
&
AUDIO_STREAM_FEATURE_PLC
)
!=
0
)
{
...
...
@@ -523,8 +513,8 @@ int audio_stream_start_full(AudioStream *stream, RtpProfile *profile, const char
,
stream
->
ms
.
rtprecv
,
NULL
);
stream
->
start_time
=
ms_time
(
NULL
);
stream
->
is_beginning
=
TRUE
;
stream
->
ms
.
start_time
=
ms_time
(
NULL
);
stream
->
ms
.
is_beginning
=
TRUE
;
return
0
;
}
...
...
@@ -664,6 +654,7 @@ AudioStream *audio_stream_new(int loc_rtp_port, int loc_rtcp_port, bool_t ipv6){
/*some filters are created right now to allow configuration by the application before start() */
stream
->
ms
.
rtpsend
=
ms_filter_new
(
MS_RTP_SEND_ID
);
stream
->
ms
.
ice_check_list
=
NULL
;
stream
->
ms
.
qi
=
ms_quality_indicator_new
(
stream
->
ms
.
session
);
if
(
ec_desc
!=
NULL
)
stream
->
ec
=
ms_filter_new_from_desc
(
ec_desc
);
...
...
@@ -770,7 +761,7 @@ void audio_stream_stop(AudioStream * stream)
if
(
stream
->
dummy
){
stop_preload_graph
(
stream
);
}
else
if
(
stream
->
start_time
!=
0
){
}
else
if
(
stream
->
ms
.
start_time
!=
0
){
ms_ticker_detach
(
stream
->
ms
.
ticker
,
stream
->
soundread
);
ms_ticker_detach
(
stream
->
ms
.
ticker
,
stream
->
ms
.
rtprecv
);
...
...
@@ -850,17 +841,11 @@ void audio_stream_mute_rtp(AudioStream *stream, bool_t val)
}
float
audio_stream_get_quality_rating
(
AudioStream
*
stream
){
if
(
stream
->
qi
){
return
ms_quality_indicator_get_rating
(
stream
->
qi
);
}
return
0
;
return
media_stream_get_quality_rating
(
&
stream
->
ms
);
}
float
audio_stream_get_average_quality_rating
(
AudioStream
*
stream
){
if
(
stream
->
qi
){
return
ms_quality_indicator_get_average_rating
(
stream
->
qi
);
}
return
0
;
return
media_stream_get_average_quality_rating
(
&
stream
->
ms
);
}
void
audio_stream_enable_zrtp
(
AudioStream
*
stream
,
OrtpZrtpParams
*
params
){
...
...
src/voip/mediastream.c
View file @
abf2a7ec
...
...
@@ -173,6 +173,7 @@ void media_stream_free(MediaStream *stream) {
if
(
stream
->
decoder
!=
NULL
)
ms_filter_destroy
(
stream
->
decoder
);
if
(
stream
->
voidsink
!=
NULL
)
ms_filter_destroy
(
stream
->
voidsink
);
if
(
stream
->
ticker
!=
NULL
)
ms_ticker_destroy
(
stream
->
ticker
);
if
(
stream
->
qi
)
ms_quality_indicator_destroy
(
stream
->
qi
);
}
void
media_stream_set_rtcp_information
(
MediaStream
*
stream
,
const
char
*
cname
,
const
char
*
tool
)
{
...
...
@@ -220,6 +221,10 @@ bool_t media_stream_enable_srtp(MediaStream *stream, enum ortp_srtp_crypto_suite
return
TRUE
;
}
const
MSQualityIndicator
*
media_stream_get_quality_indicator
(
MediaStream
*
stream
){
return
stream
->
qi
;
}
bool_t
ms_is_ipv6
(
const
char
*
remote
)
{
bool_t
ret
=
FALSE
;
#ifdef INET6
...
...
@@ -240,8 +245,37 @@ bool_t ms_is_ipv6(const char *remote) {
return
ret
;
}
void
payload_type_changed
(
RtpSession
*
session
,
unsigned
long
data
)
{
void
mediastream_
payload_type_changed
(
RtpSession
*
session
,
unsigned
long
data
)
{
MediaStream
*
stream
=
(
MediaStream
*
)
data
;
int
pt
=
rtp_session_get_recv_payload_type
(
stream
->
session
);
media_stream_change_decoder
(
stream
,
pt
);
}
void
media_stream_iterate
(
MediaStream
*
stream
){
time_t
curtime
=
ms_time
(
NULL
);
if
(
stream
->
is_beginning
&&
(
curtime
-
stream
->
start_time
>
15
)){
rtp_session_set_rtcp_report_interval
(
stream
->
session
,
5000
);
stream
->
is_beginning
=
FALSE
;
}
if
(
stream
->
ice_check_list
)
ice_check_list_process
(
stream
->
ice_check_list
,
stream
->
session
);
/*we choose to update the quality indicator as much as possible, since local statistics can be computed realtime. */
if
(
stream
->
qi
&&
curtime
>
stream
->
last_iterate_time
)
ms_quality_indicator_update_local
(
stream
->
qi
);
stream
->
last_iterate_time
=
curtime
;
}
float
media_stream_get_quality_rating
(
MediaStream
*
stream
){
if
(
stream
->
qi
){
return
ms_quality_indicator_get_rating
(
stream
->
qi
);
}
return
-
1
;
}
float
media_stream_get_average_quality_rating
(
MediaStream
*
stream
){
if
(
stream
->
qi
){
return
ms_quality_indicator_get_average_rating
(
stream
->
qi
);
}
return
-
1
;
}
src/voip/private.h
View file @
abf2a7ec
...
...
@@ -47,7 +47,7 @@ MEDIASTREAMER2_INTERNAL_EXPORT RtpSession * create_duplex_rtpsession(int loc_rtp
void
start_ticker
(
MediaStream
*
stream
);
void
payload_type_changed
(
RtpSession
*
session
,
unsigned
long
data
);
void
mediastream_
payload_type_changed
(
RtpSession
*
session
,
unsigned
long
data
);
const
char
*
media_stream_type_str
(
MediaStream
*
stream
);
...
...
src/voip/qualityindicator.c
View file @
abf2a7ec
...
...
@@ -39,6 +39,8 @@ struct _MSQualityIndicator{
uint32_t
last_ext_seq
;
uint32_t
last_late
;
int
count
;
float
cur_late_rate
;
float
cur_loss_rate
;
};
MSQualityIndicator
*
ms_quality_indicator_new
(
RtpSession
*
session
){
...
...
@@ -140,8 +142,8 @@ void ms_quality_indicator_update_local(MSQualityIndicator *qi){
if
(
lost
<
0
)
lost
=
0
;
/* will be the case at least the first time, because we don't know the initial sequence number*/
if
(
late
<
0
)
late
=
0
;
loss_rate
=
(
float
)
lost
/
(
float
)
recvcnt
;
late_rate
=
(
float
)
late
/
(
float
)
recvcnt
;
qi
->
cur_loss_rate
=
loss_rate
=
(
float
)
lost
/
(
float
)
recvcnt
;
qi
->
cur_late_rate
=
late_rate
=
(
float
)
late
/
(
float
)
recvcnt
;
qi
->
local_rating
=
compute_rating
(
loss_rate
,
0
,
late_rate
,
rtp_session_get_round_trip_propagation
(
qi
->
session
));
update_global_rating
(
qi
);
...
...
@@ -152,6 +154,14 @@ float ms_quality_indicator_get_average_rating(MSQualityIndicator *qi){
return
(
float
)(
qi
->
sum_ratings
/
(
double
)
qi
->
count
);
}
float
ms_quality_indicator_get_local_loss_rate
(
const
MSQualityIndicator
*
qi
){
return
qi
->
cur_loss_rate
;
}
float
ms_quality_indicator_get_local_late_rate
(
const
MSQualityIndicator
*
qi
){
return
qi
->
cur_late_rate
;
}
void
ms_quality_indicator_destroy
(
MSQualityIndicator
*
qi
){
ms_free
(
qi
);
}
...
...
src/voip/videostream.c
View file @
abf2a7ec
...
...
@@ -113,7 +113,7 @@ void video_stream_iterate(VideoStream *stream){
ortp_event_destroy
(
ev
);
}
}
if
(
stream
->
ms
.
ice_check_list
)
ice_check_list_process
(
stream
->
ms
.
ice_check_list
,
stream
->
ms
.
session
);
media_stream_iterate
(
&
stream
->
ms
);
}
static
void
choose_display_name
(
VideoStream
*
stream
){
...
...
@@ -138,6 +138,7 @@ VideoStream *video_stream_new(int loc_rtp_port, int loc_rtcp_port, bool_t use_ip
VideoStream
*
stream
=
(
VideoStream
*
)
ms_new0
(
VideoStream
,
1
);
stream
->
ms
.
type
=
VideoStreamType
;
stream
->
ms
.
session
=
create_duplex_rtpsession
(
loc_rtp_port
,
loc_rtcp_port
,
use_ipv6
);
stream
->
ms
.
qi
=
ms_quality_indicator_new
(
stream
->
ms
.
session
);
stream
->
ms
.
evq
=
ortp_ev_queue_new
();
stream
->
ms
.
rtpsend
=
ms_filter_new
(
MS_RTP_SEND_ID
);
stream
->
ms
.
ice_check_list
=
NULL
;
...
...
@@ -316,7 +317,7 @@ int video_stream_start (VideoStream *stream, RtpProfile *profile, const char *re
rtp_session_set_jitter_compensation
(
rtps
,
jitt_comp
);
rtp_session_signal_connect
(
stream
->
ms
.
session
,
"payload_type_changed"
,
(
RtpCallback
)
payload_type_changed
,(
unsigned
long
)
&
stream
->
ms
);
(
RtpCallback
)
mediastream_
payload_type_changed
,(
unsigned
long
)
&
stream
->
ms
);
rtp_session_get_jitter_buffer_params
(
stream
->
ms
.
session
,
&
jbp
);
jbp
.
max_packets
=
1000
;
//needed for high resolution video
...
...
@@ -454,6 +455,9 @@ int video_stream_start (VideoStream *stream, RtpProfile *profile, const char *re
/* create the ticker */
if
(
stream
->
ms
.
ticker
==
NULL
)
start_ticker
(
&
stream
->
ms
);
stream
->
ms
.
start_time
=
ms_time
(
NULL
);
stream
->
ms
.
is_beginning
=
TRUE
;
/* attach the graphs */
if
(
stream
->
source
)
...
...
tools/mediastream.c
View file @
abf2a7ec
...
...
@@ -766,7 +766,7 @@ void setup_media_streams(MediastreamDatas* args) {
}
static
void
mediastream_iterate
(
MediastreamDatas
*
args
)
{
static
void
mediastream_
tool_
iterate
(
MediastreamDatas
*
args
)
{
#ifndef WIN32
struct
pollfd
pfd
;
int
err
;
...
...
@@ -844,7 +844,7 @@ void mediastream_run_loop(MediastreamDatas* args) {
{
int
n
;
for
(
n
=
0
;
n
<
100
;
++
n
){
mediastream_iterate
(
args
);
mediastream_
tool_
iterate
(
args
);
#if defined(VIDEO_ENABLED)
if
(
args
->
video
)
video_stream_iterate
(
args
->
video
);
#endif
...
...
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