This is merely a historical archive of years 2008-2021, before the migration to mailman3.
A maintained and still updated list archive can be found at https://lists.osmocom.org/hyperkitty/list/gerrit-log@lists.osmocom.org/.
Harald Welte gerrit-no-reply at lists.osmocom.orgHarald Welte has submitted this change and it was merged. Change subject: network: autdetect rtp bind ip-address ...................................................................... network: autdetect rtp bind ip-address Currently there are two ways to set the rtp bind ip-address (local ip address where the rtp streams are bound to). It is possible to set no set an rtp bind ip, if none no address is configured, then the ip address where the mgcp service is bound to is used. On a system with multiple network interfaces it is likely that there are the remote end is not reachable through the interface that has been configured. In this case rtp ip-probing can be enabled via vty option in order to automatically detect the ip address of the interface that points towards the remote end. The autodetection can only work if the ip-address is known when a CRCX is performed. For this the remote entity must include the remote ip address in the sdp trailer. Implement probing to determine te right local ip address Add debug log to display which ip address is actually used Add a VTY option for the probing functionality. Change-Id: Ia57cf7dab8421fd3ab6e1515727db0080373485e --- M include/osmocom/mgcp/mgcp.h M include/osmocom/mgcp/mgcp_internal.h M src/libosmo-mgcp/mgcp_network.c M src/libosmo-mgcp/mgcp_protocol.c M src/libosmo-mgcp/mgcp_vty.c 5 files changed, 97 insertions(+), 20 deletions(-) Approvals: Harald Welte: Looks good to me, approved Jenkins Builder: Verified diff --git a/include/osmocom/mgcp/mgcp.h b/include/osmocom/mgcp/mgcp.h index 59147f0..42a91d8 100644 --- a/include/osmocom/mgcp/mgcp.h +++ b/include/osmocom/mgcp/mgcp.h @@ -96,6 +96,12 @@ int range_start; int range_end; int last_port; + + /* set to true to enable automatic probing + * of the local bind IP-Address, bind_addr + * (or its fall back) is used when automatic + * probing fails */ + bool bind_addr_probe; }; /* There are up to three modes in which the keep-alive dummy packet can be diff --git a/include/osmocom/mgcp/mgcp_internal.h b/include/osmocom/mgcp/mgcp_internal.h index d4c8dc9..b9c1731 100644 --- a/include/osmocom/mgcp/mgcp_internal.h +++ b/include/osmocom/mgcp/mgcp_internal.h @@ -318,12 +318,4 @@ #define PTYPE_UNDEFINED (-1) -/*! get the ip-address where the mgw application is bound on. - * \param[in] endp mgcp endpoint, that holds a copy of the VTY parameters - * \returns pointer to a string that contains the source ip-address */ -static inline const char *mgcp_net_src_addr(struct mgcp_endpoint *endp) -{ - if (endp->cfg->net_ports.bind_addr) - return endp->cfg->net_ports.bind_addr; - return endp->cfg->source_addr; -} +void mgcp_get_local_addr(char *addr, struct mgcp_conn_rtp *conn); diff --git a/src/libosmo-mgcp/mgcp_network.c b/src/libosmo-mgcp/mgcp_network.c index 3d52d07..7876b33 100644 --- a/src/libosmo-mgcp/mgcp_network.c +++ b/src/libosmo-mgcp/mgcp_network.c @@ -32,6 +32,7 @@ #include <osmocom/core/msgb.h> #include <osmocom/core/select.h> +#include <osmocom/core/socket.h> #include <osmocom/netif/rtp.h> #include <osmocom/mgcp/mgcp.h> #include <osmocom/mgcp/mgcp_common.h> @@ -51,6 +52,56 @@ MGCP_PROTO_RTP, MGCP_PROTO_RTCP, }; + +/*! Determine the local rtp bind IP-address. + * \param[out] addr caller provided memory to store the resulting IP-Address + * \param[in] endp mgcp endpoint, that holds a copy of the VTY parameters + * + * The local bind IP-address is automatically selected by probing the + * IP-Address of the interface that is pointing towards the remote IP-Address, + * if no remote IP-Address is known yet, the statically configured + * IP-Addresses are used as fallback. */ +void mgcp_get_local_addr(char *addr, struct mgcp_conn_rtp *conn) +{ + + struct mgcp_endpoint *endp; + int rc; + endp = conn->conn->endp; + + /* Try probing the local IP-Address */ + if (endp->cfg->net_ports.bind_addr_probe && conn->end.addr.s_addr != 0) { + rc = osmo_sock_local_ip(addr, inet_ntoa(conn->end.addr)); + if (rc < 0) + LOGP(DRTP, LOGL_ERROR, + "endpoint:%x CI:%i local interface auto detection failed, using configured addresses...\n", + ENDPOINT_NUMBER(endp), conn->conn->id); + else { + LOGP(DRTP, LOGL_DEBUG, + "endpoint:%x CI:%i selected local rtp bind ip %s by probing using remote ip %s\n", + ENDPOINT_NUMBER(endp), conn->conn->id, addr, + inet_ntoa(conn->end.addr)); + return; + } + } + + /* Select from preconfigured IP-Addresses */ + if (endp->cfg->net_ports.bind_addr) { + /* Check there is a bind IP for the RTP traffic configured, + * if so, use that IP-Address */ + strncpy(addr, endp->cfg->net_ports.bind_addr, INET_ADDRSTRLEN); + LOGP(DRTP, LOGL_DEBUG, + "endpoint:%x CI:%i using configured rtp bind ip as local bind ip %s\n", + ENDPOINT_NUMBER(endp), conn->conn->id, addr); + } else { + /* No specific bind IP is configured for the RTP traffic, so + * assume the IP where we listen for incoming MGCP messages + * as bind IP */ + strncpy(addr, endp->cfg->source_addr, INET_ADDRSTRLEN); + LOGP(DRTP, LOGL_DEBUG, + "endpoint:%x CI:%i using mgcp bind ip as local rtp bind ip: %s\n", + ENDPOINT_NUMBER(endp), conn->conn->id, addr); + } +} /* This does not need to be a precision timestamp and * is allowed to wrap quite fast. The returned value is @@ -1158,6 +1209,7 @@ { char name[512]; struct mgcp_rtp_end *end; + char local_ip_addr[INET_ADDRSTRLEN]; snprintf(name, sizeof(name), "%s-%u", conn->conn->name, conn->conn->id); end = &conn->end; @@ -1182,7 +1234,9 @@ end->rtcp.data = conn; end->rtcp.cb = rtp_data_net; - return bind_rtp(endp->cfg, mgcp_net_src_addr(endp), end, + mgcp_get_local_addr(local_ip_addr, conn); + + return bind_rtp(endp->cfg, local_ip_addr, end, ENDPOINT_NUMBER(endp)); } diff --git a/src/libosmo-mgcp/mgcp_protocol.c b/src/libosmo-mgcp/mgcp_protocol.c index 4826790..8c6bd6e 100644 --- a/src/libosmo-mgcp/mgcp_protocol.c +++ b/src/libosmo-mgcp/mgcp_protocol.c @@ -203,13 +203,16 @@ int rc; struct msgb *result; char osmux_extension[strlen("\nX-Osmux: 255") + 1]; + char local_ip_addr[INET_ADDRSTRLEN]; sdp = msgb_alloc_headroom(4096, 128, "sdp record"); if (!sdp) return NULL; - if (!addr) - addr = mgcp_net_src_addr(endp); + if (!addr) { + mgcp_get_local_addr(local_ip_addr, conn); + addr = local_ip_addr; + } if (conn->osmux.state == OSMUX_STATE_NEGOTIATING) { sprintf(osmux_extension, "\nX-Osmux: %u", conn->osmux.cid); @@ -597,12 +600,6 @@ goto error2; } - mgcp_rtp_end_config(endp, 0, &conn->end); - - if (allocate_port(endp, conn) != 0) { - goto error2; - } - /* Annotate Osmux circuit ID and set it to negotiating state until this * is fully set up from the dummy load. */ conn->osmux.state = OSMUX_STATE_DISABLED; @@ -630,6 +627,12 @@ conn->end.force_output_ptime = 1; } + mgcp_rtp_end_config(endp, 0, &conn->end); + + if (allocate_port(endp, conn) != 0) { + goto error2; + } + if (setup_rtp_processing(endp, conn) != 0) { LOGP(DLMGCP, LOGL_ERROR, "CRCX: endpoint:%x could not start RTP processing!\n", diff --git a/src/libosmo-mgcp/mgcp_vty.c b/src/libosmo-mgcp/mgcp_vty.c index 7107bcc..7ff1fdd 100644 --- a/src/libosmo-mgcp/mgcp_vty.c +++ b/src/libosmo-mgcp/mgcp_vty.c @@ -70,11 +70,13 @@ vty_out(vty, " rtp net-range %u %u%s", g_cfg->net_ports.range_start, g_cfg->net_ports.range_end, VTY_NEWLINE); - if (g_cfg->net_ports.bind_addr) vty_out(vty, " rtp net-bind-ip %s%s", g_cfg->net_ports.bind_addr, VTY_NEWLINE); - + if (g_cfg->net_ports.bind_addr_probe) + vty_out(vty, " rtp ip-probing%s", VTY_NEWLINE); + else + vty_out(vty, " no rtp ip-probing%s", VTY_NEWLINE); vty_out(vty, " rtp ip-dscp %d%s", g_cfg->endp_dscp, VTY_NEWLINE); if (g_cfg->trunk.keepalive_interval == MGCP_KEEPALIVE_ONCE) vty_out(vty, " rtp keep-alive once%s", VTY_NEWLINE); @@ -317,6 +319,24 @@ { talloc_free(g_cfg->net_ports.bind_addr); g_cfg->net_ports.bind_addr = NULL; + return CMD_SUCCESS; +} + +DEFUN(cfg_mgcp_rtp_net_bind_ip_probing, + cfg_mgcp_rtp_net_bind_ip_probing_cmd, + "rtp ip-probing", + RTP_STR "automatic rtp bind ip selection\n") +{ + g_cfg->net_ports.bind_addr_probe = true; + return CMD_SUCCESS; +} + +DEFUN(cfg_mgcp_rtp_no_net_bind_ip_probing, + cfg_mgcp_rtp_no_net_bind_ip_probing_cmd, + "no rtp ip-probing", + NO_STR RTP_STR "no automatic rtp bind ip selection\n") +{ + g_cfg->net_ports.bind_addr_probe = false; return CMD_SUCCESS; } @@ -1163,6 +1183,8 @@ install_element(MGCP_NODE, &cfg_mgcp_rtp_net_range_cmd); install_element(MGCP_NODE, &cfg_mgcp_rtp_net_bind_ip_cmd); install_element(MGCP_NODE, &cfg_mgcp_rtp_no_net_bind_ip_cmd); + install_element(MGCP_NODE, &cfg_mgcp_rtp_net_bind_ip_probing_cmd); + install_element(MGCP_NODE, &cfg_mgcp_rtp_no_net_bind_ip_probing_cmd); install_element(MGCP_NODE, &cfg_mgcp_rtp_ip_dscp_cmd); install_element(MGCP_NODE, &cfg_mgcp_rtp_ip_tos_cmd); install_element(MGCP_NODE, &cfg_mgcp_rtp_force_ptime_cmd); -- To view, visit https://gerrit.osmocom.org/4650 To unsubscribe, visit https://gerrit.osmocom.org/settings Gerrit-MessageType: merged Gerrit-Change-Id: Ia57cf7dab8421fd3ab6e1515727db0080373485e Gerrit-PatchSet: 1 Gerrit-Project: osmo-mgw Gerrit-Branch: master Gerrit-Owner: dexter <pmaier at sysmocom.de> Gerrit-Reviewer: Harald Welte <laforge at gnumonks.org> Gerrit-Reviewer: Jenkins Builder