Review at  https://gerrit.osmocom.org/6840

a_iface: fix reset handing

When osmo-msc restarts it looses all information about the BSC. The
BSC will not be aware of the reboot and on the next communication
attemt it will notice that something is wrong and start the reset
procedure on his side. osmo-msc will receive the reset messages
and send a reset.

The reset is received. Osmo-msc detects that no context information
is created yet. The context is created. Then it is checked if the
UNITTDATA message that came in is a reset. If it is one. Nothing
happens. The UNITTDATA is passed on and triggers the RESET-ACK
some layers above. Unfortunately by the current code this also
means that no reset FSM is created and therefore a_reset_conn_ready()
can never be true. Which means it will also drop any legitimate
reset from the BSC in the future.

- Ensure that the reset FSM is always created when a new BSC
  context is created

- Make sure that reset related traffic always passes so that
  the higher layers can handle the procedure properly

Change-Id: I3fdcec5dbeaa0e21fd6a92568a623faa368239be
---
M src/libmsc/a_iface.c
1 file changed, 17 insertions(+), 15 deletions(-)


  git pull ssh://gerrit.osmocom.org:29418/osmo-msc refs/changes/40/6840/1

diff --git a/src/libmsc/a_iface.c b/src/libmsc/a_iface.c
index 86c2e04..79b1b4c 100644
--- a/src/libmsc/a_iface.c
+++ b/src/libmsc/a_iface.c
@@ -478,7 +478,7 @@
        bsc_ctx->reset = a_reset_alloc(bsc_ctx, bsc_name, a_reset_cb, bsc_ctx, 
already_connected);
 }
 
-/* determine if given msg is a BSSMAP RESET (true) or not (false) */
+/* determine if given msg is BSSMAP RESET related (true) or not (false) */
 static bool bssmap_is_reset(struct msgb *msg)
 {
        struct bssmap_header *bs = (struct bssmap_header *)msgb_l2(msg);
@@ -490,6 +490,9 @@
                return false;
 
        if (msg->l2h[sizeof(*bs)] == BSS_MAP_MSG_RESET)
+               return true;
+
+       if (msg->l2h[sizeof(*bs)] == BSS_MAP_MSG_RESET_ACKNOWLEDGE)
                return true;
 
        return false;
@@ -555,26 +558,25 @@
 
        case OSMO_PRIM(OSMO_SCU_PRIM_N_UNITDATA, PRIM_OP_INDICATION):
                /* Handle inbound UNITDATA */
+
+               /* Get BSC context, create a new one if necessary */
                a_conn_info.bsc = 
get_bsc_context_by_sccp_addr(&scu_prim->u.unitdata.calling_addr);
                if (!a_conn_info.bsc) {
                        /* We haven't heard from this BSC before, allocate it */
                        a_conn_info.bsc = 
add_bsc(&scu_prim->u.unitdata.called_addr,
                                                
&scu_prim->u.unitdata.calling_addr, scu);
-                       /* if this not an inbound RESET, trigger an outbound 
RESET */
-                       if (!bssmap_is_reset(oph->msg)) {
-                               LOGP(DBSSAP, LOGL_NOTICE, "Ignoring 
N-UNITDATA.ind(%s), BSC not reset yet\n",
-                                       msgb_hexdump_l2(oph->msg));
-                               a_start_reset(a_conn_info.bsc, false);
-                               break;
-                       }
-               } else {
-                       /* This BSC is already known to us, check if we have 
been through reset yet */
-                       if (a_reset_conn_ready(a_conn_info.bsc->reset) == 
false) {
-                               LOGP(DBSSAP, LOGL_NOTICE, "Ignoring 
N-UNITDATA.ind(%s), BSC not reset yet\n",
-                                       msgb_hexdump_l2(oph->msg));
-                               break;
-                       }
+                       /* Make sure that reset procedure is started */
+                       a_start_reset(a_conn_info.bsc, false);
                }
+
+               /* As long as we are in the reset phase, only reset related 
BSSMAP messages may pass
+                * beond here. */
+               if (!bssmap_is_reset(oph->msg) && 
a_reset_conn_ready(a_conn_info.bsc->reset) == false) {
+                       LOGP(DBSSAP, LOGL_NOTICE, "Ignoring N-UNITDATA.ind(%s), 
BSC not reset yet\n",
+                            msgb_hexdump_l2(oph->msg));
+                       break;
+               }
+
                DEBUGP(DBSSAP, "N-UNITDATA.ind(%s)\n", 
msgb_hexdump_l2(oph->msg));
                a_sccp_rx_udt(scu, &a_conn_info, oph->msg);
                break;

-- 
To view, visit https://gerrit.osmocom.org/6840
To unsubscribe, visit https://gerrit.osmocom.org/settings

Gerrit-MessageType: newchange
Gerrit-Change-Id: I3fdcec5dbeaa0e21fd6a92568a623faa368239be
Gerrit-PatchSet: 1
Gerrit-Project: osmo-msc
Gerrit-Branch: master
Gerrit-Owner: dexter <pma...@sysmocom.de>

Reply via email to