diff --git a/README.md b/README.md index 5ccf9a518..5ff28cc49 100644 --- a/README.md +++ b/README.md @@ -1184,6 +1184,10 @@ Optionally included keys are: When processing a non-OSRTP answer in response to an OSRTP offer, accept the OSRTP offer anyway. Results in RTP/SRTP transcoding. +* `endpoint-learning` + + Contains one of the strings `off`, `immediate`, `delayed` or `heuristic`. This tells rtpengine which endpoint learning algorithm to use and overrides the `endpoint-learning` configuration option. This option can also be put into the `flags` list using a prefix of `endpoint-learning-`. + * `record call` Contains one of the strings `yes`, `no`, `on` or `off`. This tells the rtpengine diff --git a/daemon/call.c b/daemon/call.c index a1aba82b5..76998dd7c 100644 --- a/daemon/call.c +++ b/daemon/call.c @@ -1102,6 +1102,10 @@ static void __fill_stream(struct packet_stream *ps, const struct endpoint *epp, dtls_shutdown(ps); } + /* endpont-learning setup */ + if (flags) + ps->el_flags = flags->el_option; + if (ps->selected_sfd) ilog(LOG_DEBUG, "set FILLED flag for stream, local %s remote %s%s%s", endpoint_print_buf(&ps->selected_sfd->socket.local), diff --git a/daemon/call_interfaces.c b/daemon/call_interfaces.c index c48e90f38..472a8611e 100644 --- a/daemon/call_interfaces.c +++ b/daemon/call_interfaces.c @@ -568,6 +568,25 @@ INLINE void ng_osrtp_option(struct sdp_ng_flags *out, str *s, void *dummy) { } } +INLINE void ng_el_option(struct sdp_ng_flags *out, str *s, void *dummy) { + switch (__csh_lookup(s)) { + case CSH_LOOKUP("off"): + out->el_option = EL_OFF; + break; + case CSH_LOOKUP("immediate"): + out->el_option = EL_IMMEDIATE; + break; + case CSH_LOOKUP("delayed"): + out->el_option = EL_DELAYED; + break; + case CSH_LOOKUP("heuristic"): + out->el_option = EL_HEURISTIC; + break; + default: + ilog(LOG_WARN, "Unknown 'endpoint-learning' flag encountered: '" STR_FORMAT "'", + STR_FMT(s)); + } +} #ifdef WITH_TRANSCODING INLINE void ng_t38_option(struct sdp_ng_flags *out, str *s, void *dummy) { @@ -920,6 +939,8 @@ static void call_ng_flags_flags(struct sdp_ng_flags *out, str *s, void *dummy) { if (call_ng_flags_prefix(out, s, "codec-except-", call_ng_flags_str_ht, &out->codec_except)) return; + if (call_ng_flags_prefix(out, s, "endpoint-learning-", ng_el_option, NULL)) + return; #ifdef WITH_TRANSCODING if (out->opmode == OP_OFFER || out->opmode == OP_REQUEST || out->opmode == OP_PUBLISH) { if (call_ng_flags_prefix(out, s, "transcode-", call_ng_flags_codec_list, @@ -959,6 +980,7 @@ void call_ng_flags_init(struct sdp_ng_flags *out, enum call_opmode opmode) { out->trust_address = trust_address_def; out->dtls_passive = dtls_passive_def; out->dtls_reverse_passive = dtls_passive_def; + out->el_option = rtpe_config.endpoint_learning; } static void call_ng_process_flags(struct sdp_ng_flags *out, bencode_item_t *input, enum call_opmode opmode) { @@ -1126,6 +1148,7 @@ static void call_ng_process_flags(struct sdp_ng_flags *out, bencode_item_t *inpu call_ng_flags_list(out, input, "sdes", ng_sdes_option, NULL); call_ng_flags_list(out, input, "OSRTP", ng_osrtp_option, NULL); call_ng_flags_list(out, input, "osrtp", ng_osrtp_option, NULL); + call_ng_flags_list(out, input, "endpoint-learning", ng_el_option, NULL); #ifdef WITH_TRANSCODING call_ng_flags_list(out, input, "T38", ng_t38_option, NULL); call_ng_flags_list(out, input, "t38", ng_t38_option, NULL); diff --git a/daemon/media_socket.c b/daemon/media_socket.c index 4e103e879..1769b88a5 100644 --- a/daemon/media_socket.c +++ b/daemon/media_socket.c @@ -2000,7 +2000,7 @@ static int media_packet_address_check(struct packet_handler_ctx *phc) PS_SET(phc->mp.stream, RECEIVED); /* do not pay attention to source addresses of incoming packets for asymmetric streams */ - if (MEDIA_ISSET(phc->mp.media, ASYMMETRIC) || rtpe_config.endpoint_learning == EL_OFF) + if (MEDIA_ISSET(phc->mp.media, ASYMMETRIC) || phc->mp.stream->el_flags == EL_OFF) PS_SET(phc->mp.stream, CONFIRMED); /* confirm sinks for unidirectional streams in order to kernelize */ @@ -2055,10 +2055,10 @@ static int media_packet_address_check(struct packet_handler_ctx *phc) const struct endpoint *use_endpoint_confirm = &phc->mp.fsin; - if (rtpe_config.endpoint_learning == EL_IMMEDIATE) + if (phc->mp.stream->el_flags == EL_IMMEDIATE) goto confirm_now; - if (rtpe_config.endpoint_learning == EL_HEURISTIC + if (phc->mp.stream->el_flags == EL_HEURISTIC && phc->mp.stream->advertised_endpoint.address.family && phc->mp.stream->advertised_endpoint.port) { diff --git a/include/call.h b/include/call.h index 27cad8f2e..bcfc81a1b 100644 --- a/include/call.h +++ b/include/call.h @@ -330,6 +330,7 @@ struct packet_stream { GHashTable *rtp_stats; /* LOCK: call->master_lock */ struct rtp_stats *rtp_stats_cache; unsigned int stats_flags; + enum endpoint_learning el_flags; #if RTP_LOOP_PROTECT /* LOCK: in_lock: */ diff --git a/include/call_interfaces.h b/include/call_interfaces.h index 2d17cd889..1cb4defef 100644 --- a/include/call_interfaces.h +++ b/include/call_interfaces.h @@ -74,6 +74,7 @@ struct sdp_ng_flags { MEO_BKW, MEO_BOTH, } media_echo:3; + enum endpoint_learning el_option; unsigned int asymmetric:1, protocol_accept:1, no_redis_update:1,