pespin has uploaded this change for review. ( 
https://gerrit.osmocom.org/c/libosmo-sigtran/+/42117?usp=email )


Change subject: xua_asp_fsm: Error on ASP UP (ACK) with non-unique ASP 
Identifier
......................................................................

xua_asp_fsm: Error on ASP UP (ACK) with non-unique ASP Identifier

Following RFC4666:
"""
   The "Invalid ASP Identifier" error is sent by an SGP in response to
   an ASP Up message with an invalid (i.e., non-unique) ASP Identifier
"""

Change-Id: I2d422acaa2f04c7d1eebd92c3185c4f5476a1789
---
M src/ss7_as.c
M src/ss7_as.h
M src/ss7_asp.c
M src/ss7_asp.h
M src/xua_asp_fsm.c
5 files changed, 60 insertions(+), 4 deletions(-)



  git pull ssh://gerrit.osmocom.org:29418/libosmo-sigtran 
refs/changes/17/42117/1

diff --git a/src/ss7_as.c b/src/ss7_as.c
index 35c85f7..7e3f172 100644
--- a/src/ss7_as.c
+++ b/src/ss7_as.c
@@ -376,6 +376,29 @@
        return !!ss7_as_asp_assoc_find(as, asp);
 }

+/*! \brief Find ASP with a given announced remote ASP Id
+ *  \param[in] as Application Server in which to look for \ref asp
+ *  \param[in] asp_id M3UA/SUA ASP Identifier
+ *  \param[in] excl_asp If not NULL, skip this asp from the candidates.
+ *  \returns the asp object if found, NULL otherwise */
+struct osmo_ss7_asp *ss7_as_find_asp_by_remote_asp_id(const struct osmo_ss7_as 
*as, uint32_t asp_id,
+                                                     const struct osmo_ss7_asp 
*excl_asp)
+{
+       struct ss7_as_asp_assoc *assoc;
+
+       llist_for_each_entry(assoc, &as->assoc_asp_list, as_entry) {
+               struct osmo_ss7_asp *asp = assoc->asp;
+               if (!asp->remote_asp_id_present)
+                       continue;
+               if (assoc->asp->remote_asp_id != asp_id)
+                       continue;
+               if (excl_asp == assoc->asp)
+                       continue;
+               return asp;
+       }
+       return NULL;
+}
+
 /* Determine which role (SG/ASP/IPSP) we operate in.
  * return enum osmo_ss7_asp_role on success, negative otherwise. */
 int ss7_as_get_local_role(const struct osmo_ss7_as *as)
diff --git a/src/ss7_as.h b/src/ss7_as.h
index 2e7f484..793cb26 100644
--- a/src/ss7_as.h
+++ b/src/ss7_as.h
@@ -183,6 +183,8 @@
 int ss7_as_add_asp(struct osmo_ss7_as *as, struct osmo_ss7_asp *asp);
 int ss7_as_del_asp(struct osmo_ss7_as *as, struct osmo_ss7_asp *asp);
 int ss7_as_get_local_role(const struct osmo_ss7_as *as);
+struct osmo_ss7_asp *ss7_as_find_asp_by_remote_asp_id(const struct osmo_ss7_as 
*as, uint32_t asp_id,
+                                                     const struct osmo_ss7_asp 
*excl_asp);
 void ss7_as_loadshare_binding_table_reset(struct osmo_ss7_as *as);

 void ss7_as_del_asp_update_llist_round_robin(struct osmo_ss7_as *as, struct 
osmo_ss7_asp *asp, struct ss7_as_asp_assoc **state);
diff --git a/src/ss7_asp.c b/src/ss7_asp.c
index 9b8f164..40433d0 100644
--- a/src/ss7_asp.c
+++ b/src/ss7_asp.c
@@ -1623,6 +1623,17 @@
        return tmode;
 }

+bool ss7_asp_check_remote_asp_id_unique(const struct osmo_ss7_asp *asp, 
uint32_t remote_asp_id)
+{
+       const struct ss7_as_asp_assoc *assoc;
+
+       llist_for_each_entry(assoc, &asp->assoc_as_list, asp_entry) {
+               if (ss7_as_find_asp_by_remote_asp_id(assoc->as, remote_asp_id, 
asp))
+                       return false;
+       }
+       return true;
+}
+
 /* process a primitive from the xUA Layer Manager (LM) */
 int osmo_xlm_sap_down(struct osmo_ss7_asp *asp, struct osmo_prim_hdr *oph)
 {
diff --git a/src/ss7_asp.h b/src/ss7_asp.h
index 75be6cc..7bce2d4 100644
--- a/src/ss7_asp.h
+++ b/src/ss7_asp.h
@@ -196,6 +196,7 @@
 struct osmo_ss7_as *ss7_asp_get_first_as(const struct osmo_ss7_asp *asp);

 int ss7_asp_determine_traf_mode(const struct osmo_ss7_asp *asp);
+bool ss7_asp_check_remote_asp_id_unique(const struct osmo_ss7_asp *asp, 
uint32_t remote_asp_id);

 #define LOGPASP(asp, subsys, level, fmt, args ...) \
        _LOGSS7((asp)->inst, subsys, level, "ASP(%s) " fmt, (asp)->cfg.name, ## 
args)
diff --git a/src/xua_asp_fsm.c b/src/xua_asp_fsm.c
index 3584b84..b1bbec6 100644
--- a/src/xua_asp_fsm.c
+++ b/src/xua_asp_fsm.c
@@ -489,6 +489,7 @@
        dispatch_to_all_as(asp->fi, XUA_ASPAS_ASP_DOWN_IND, asp);

        /* Implicit clean up tasks: */
+       asp->remote_asp_id_present = false;
        llist_for_each_entry_safe(assoc, assoc2, &asp->assoc_as_list, 
asp_entry) {
                struct osmo_ss7_as *as = assoc->as;
 #ifdef WITH_TCAP_LOADSHARING
@@ -547,6 +548,7 @@
        struct xua_asp_fsm_priv *xafp = fi->priv;
        struct osmo_ss7_asp *asp = xafp->asp;
        struct xua_msg_part *asp_id_ie;
+       uint32_t asp_id;

        check_stop_t_ack(fi, event);

@@ -560,7 +562,12 @@
                ENSURE_ASP_OR_IPSP(fi, event);
                /* Optional ASP Identifier */
                if ((asp_id_ie = xua_msg_find_tag(data, SUA_IEI_ASP_ID))) {
-                       asp->remote_asp_id = xua_msg_part_get_u32(asp_id_ie);
+                       asp_id = xua_msg_part_get_u32(asp_id_ie);
+                       if (!ss7_asp_check_remote_asp_id_unique(asp, asp_id)) {
+                               peer_send_error(fi, M3UA_ERR_INVAL_ASP_ID);
+                               return;
+                       }
+                       asp->remote_asp_id = asp_id;
                        asp->remote_asp_id_present = true;
                }
                osmo_fsm_inst_state_chg(fi, XUA_ASP_S_INACTIVE, 0, 0);
@@ -569,9 +576,15 @@
                break;
        case XUA_ASP_E_ASPSM_ASPUP:
                ENSURE_SG_OR_IPSP(fi, event);
-               /* Optional ASP Identifier: Store for NTFY */
+               /* Optional ASP Identifier */
                if ((asp_id_ie = xua_msg_find_tag(data, SUA_IEI_ASP_ID))) {
-                       asp->remote_asp_id = xua_msg_part_get_u32(asp_id_ie);
+                       asp_id = xua_msg_part_get_u32(asp_id_ie);
+                       if (!ss7_asp_check_remote_asp_id_unique(asp, asp_id)) {
+                               peer_send_error(fi, M3UA_ERR_INVAL_ASP_ID);
+                               return;
+                       }
+                       /* Store for NTFY */
+                       asp->remote_asp_id = asp_id;
                        asp->remote_asp_id_present = true;
                }
                /* send ACK */
@@ -627,6 +640,7 @@
        struct xua_msg *xua_in;
        uint32_t traf_mode = 0;
        struct xua_msg_part *part;
+       uint32_t asp_id;
        int i;

        check_stop_t_ack(fi, event);
@@ -644,7 +658,12 @@
                ENSURE_IPSP(fi, event);
                /* Optional ASP Identifier */
                if ((asp_id_ie = xua_msg_find_tag(data, SUA_IEI_ASP_ID))) {
-                       asp->remote_asp_id = xua_msg_part_get_u32(asp_id_ie);
+                       asp_id = xua_msg_part_get_u32(asp_id_ie);
+                       if (!ss7_asp_check_remote_asp_id_unique(asp, asp_id)) {
+                               peer_send_error(fi, M3UA_ERR_INVAL_ASP_ID);
+                               return;
+                       }
+                       asp->remote_asp_id = asp_id;
                        asp->remote_asp_id_present = true;
                }
                /* inform layer manager */

--
To view, visit https://gerrit.osmocom.org/c/libosmo-sigtran/+/42117?usp=email
To unsubscribe, or for help writing mail filters, visit 
https://gerrit.osmocom.org/settings?usp=email

Gerrit-MessageType: newchange
Gerrit-Project: libosmo-sigtran
Gerrit-Branch: master
Gerrit-Change-Id: I2d422acaa2f04c7d1eebd92c3185c4f5476a1789
Gerrit-Change-Number: 42117
Gerrit-PatchSet: 1
Gerrit-Owner: pespin <[email protected]>

Reply via email to