]> git.ipfire.org Git - thirdparty/asterisk.git/commitdiff
res_pjsip: Make message_filter and session multipart aware
authorGeorge Joseph <gjoseph@digium.com>
Mon, 10 Jan 2022 13:44:12 +0000 (06:44 -0700)
committerGeorge Joseph <gjoseph@digium.com>
Mon, 17 Jan 2022 17:19:18 +0000 (11:19 -0600)
Neither pjsip_message_filter's filter_on_tx_message() nor
res_pjsip_session's session_outgoing_nat_hook() were multipart
aware and just assumed that an SDP would be the only thing in
a message body.  Both were changed to use the new
pjsip_get_sdp_info() function which searches for an sdp in
both single- and multi- part message bodies.

ASTERISK-29813

Change-Id: I8f5b8cfdc27f1d4bd3e7491ea9090951a4525c56

res/res_pjsip/pjsip_message_filter.c
res/res_pjsip_session.c

index 2e3efcdcb19e5258aa024a2339433d40281d45ff..ceb8913970ebde0b416a05793cdc28844624058a 100644 (file)
@@ -230,6 +230,8 @@ static pj_status_t filter_on_tx_message(pjsip_tx_data *tdata)
        pjsip_via_hdr *via;
        pjsip_fromto_hdr *from;
        pjsip_tpselector sel;
+       pjsip_sdp_info *sdp_info;
+       pjmedia_sdp_session *sdp;
 
        sanitize_tdata(tdata);
 
@@ -325,10 +327,23 @@ static pj_status_t filter_on_tx_message(pjsip_tx_data *tdata)
                }
        }
 
-       /* Update the SDP if it is present */
-       if (tdata->msg->body && ast_sip_is_content_type(&tdata->msg->body->content_type, "application", "sdp") &&
-               multihomed_rewrite_sdp(tdata->msg->body->data)) {
-               struct pjmedia_sdp_session *sdp = tdata->msg->body->data;
+       /* If there's no body in the tdata we can just return here. */
+       if (!tdata->msg->body) {
+               return PJ_SUCCESS;
+       }
+
+       /*
+        * pjsip_get_sdp_info will search for an SDP even if it's in
+        * a multipart message body.
+        */
+       sdp_info = pjsip_get_sdp_info(tdata->pool, tdata->msg->body, NULL, &pjsip_media_type_application_sdp);
+       if (sdp_info->sdp_err != PJ_SUCCESS || !sdp_info->sdp) {
+               return PJ_SUCCESS;
+       }
+
+       sdp = sdp_info->sdp;
+
+       if (multihomed_rewrite_sdp(sdp)) {
                static const pj_str_t STR_IP4 = { "IP4", 3 };
                static const pj_str_t STR_IP6 = { "IP6", 3 };
                pj_str_t STR_IP;
index 030688657c3f27065d4a3b428b9fc49fce0fda35..3c55af75c27b0092df96e80c139669cbcad380cd 100644 (file)
@@ -5418,19 +5418,25 @@ static void session_outgoing_nat_hook(pjsip_tx_data *tdata, struct ast_sip_trans
        RAII_VAR(struct ast_sip_transport_state *, transport_state, ast_sip_get_transport_state(ast_sorcery_object_get_id(transport)), ao2_cleanup);
        struct ast_sip_nat_hook *hook = ast_sip_mod_data_get(
                tdata->mod_data, session_module.id, MOD_DATA_NAT_HOOK);
-       struct pjmedia_sdp_session *sdp;
+       pjsip_sdp_info *sdp_info;
+       pjmedia_sdp_session *sdp;
        pjsip_dialog *dlg = pjsip_tdata_get_dlg(tdata);
        RAII_VAR(struct ast_sip_session *, session, dlg ? ast_sip_dialog_get_session(dlg) : NULL, ao2_cleanup);
        int stream;
 
-       /* SDP produced by us directly will never be multipart */
-       if (!transport_state || hook || !tdata->msg->body ||
-               !ast_sip_are_media_types_equal(&tdata->msg->body->content_type, &pjsip_media_type_application_sdp) ||
-               ast_strlen_zero(transport->external_media_address)) {
+       /*
+        * If there's no transport_state or body, or the hook
+        * has already been run, just return.
+        */
+       if (ast_strlen_zero(transport->external_media_address) || !transport_state || hook || !tdata->msg->body) {
                return;
        }
 
-       sdp = tdata->msg->body->data;
+       sdp_info = pjsip_get_sdp_info(tdata->pool, tdata->msg->body, NULL, &pjsip_media_type_application_sdp);
+       if (sdp_info->sdp_err != PJ_SUCCESS || !sdp_info->sdp) {
+               return;
+       }
+       sdp = sdp_info->sdp;
 
        if (sdp->conn) {
                char host[NI_MAXHOST];