fixeria has uploaded this change for review. ( 
https://gerrit.osmocom.org/c/osmo-bsc/+/42590?usp=email )


Change subject: assignment_fsm: check ipaccess channel mode support
......................................................................

assignment_fsm: check ipaccess channel mode support

Add ipacc_chan_mode_supported(), which checks the NM_IPAC_F_CHANM_*
flags stored in the Baseband Transceiver's MO state (populated during
OML bring-up) to decide whether the BTS can handle a requested channel
mode.  If the IE containing supported channel modes was never received,
the function returns true as if the given mode was supported.

Without this change, requesting a channel mode not supported by the
BTS results in a NACK to the RSL Channel Activation, which causes
the lchan to be marked as BROKEN and thus unavailable.

Change-Id: I680ba7993786f5486d671f931e75df4543670a37
Related: OS#6324
---
M src/osmo-bsc/assignment_fsm.c
1 file changed, 102 insertions(+), 3 deletions(-)



  git pull ssh://gerrit.osmocom.org:29418/osmo-bsc refs/changes/90/42590/1

diff --git a/src/osmo-bsc/assignment_fsm.c b/src/osmo-bsc/assignment_fsm.c
index 11408d6..54a57aa 100644
--- a/src/osmo-bsc/assignment_fsm.c
+++ b/src/osmo-bsc/assignment_fsm.c
@@ -365,6 +365,86 @@
                                                            
new_lchan->ts->max_primary_lchans : 0));
 }

+/* Check whether the ipaccess BTS supports the requested channel mode.
+ * Returns false if the BTS has reported its supported channel modes and the
+ * requested mode is absent from that list.  Returns true if the Supported
+ * Features IE was never received (older osmo-bts versions do not send it). */
+static bool ipacc_chan_mode_supported(const struct gsm_lchan *lchan,
+                                     const struct channel_mode_and_rate 
*ch_mode_rate)
+{
+       const struct ipacc_supp_feat *feat =
+               &lchan->ts->trx->bb_transc.mo.ipaccess.chan_modes;
+       uint32_t flag = 0;
+
+       /* Supported Features IE was not received */
+       if (!feat->present)
+               return true;
+
+       switch (gsm48_chan_mode_to_non_vamos(ch_mode_rate->chan_mode)) {
+       case GSM48_CMODE_SPEECH_V1:
+               flag = (lchan->type == GSM_LCHAN_TCH_H)
+                       ? NM_IPAC_F_CHANM_SPEECH_HS : NM_IPAC_F_CHANM_SPEECH_FS;
+               break;
+       case GSM48_CMODE_SPEECH_EFR:
+               flag = NM_IPAC_F_CHANM_SPEECH_EFS;
+               break;
+       case GSM48_CMODE_SPEECH_AMR:
+               flag = (lchan->type == GSM_LCHAN_TCH_H)
+                       ? NM_IPAC_F_CHANM_SPEECH_AHS : 
NM_IPAC_F_CHANM_SPEECH_AFS;
+               break;
+       case GSM48_CMODE_DATA_3k6:
+       case GSM48_CMODE_DATA_6k0:
+       case GSM48_CMODE_DATA_12k0:
+       case GSM48_CMODE_DATA_14k5:
+               if (ch_mode_rate->data_transparent) {
+                       switch (ch_mode_rate->data_rate.t) {
+                       case RSL_CMOD_CSD_T_1200_75:
+                               flag = NM_IPAC_F_CHANM_CSD_T_1200_75;
+                               break;
+                       case RSL_CMOD_CSD_T_600:
+                               flag = NM_IPAC_F_CHANM_CSD_T_600;
+                               break;
+                       case RSL_CMOD_CSD_T_1k2:
+                               flag = NM_IPAC_F_CHANM_CSD_T_1k2;
+                               break;
+                       case RSL_CMOD_CSD_T_2k4:
+                               flag = NM_IPAC_F_CHANM_CSD_T_2k4;
+                               break;
+                       case RSL_CMOD_CSD_T_4k8:
+                               flag = NM_IPAC_F_CHANM_CSD_T_4k8;
+                               break;
+                       case RSL_CMOD_CSD_T_9k6:
+                               flag = NM_IPAC_F_CHANM_CSD_T_9k6;
+                               break;
+                       case RSL_CMOD_CSD_T_14k4:
+                               flag = NM_IPAC_F_CHANM_CSD_T_14k4;
+                               break;
+                       default:
+                               return true; /* unhandled T rate */
+                       }
+               } else {
+                       switch (ch_mode_rate->data_rate.nt) {
+                       case RSL_CMOD_CSD_NT_6k0:
+                               flag = NM_IPAC_F_CHANM_CSD_NT_4k8;
+                               break;
+                       case RSL_CMOD_CSD_NT_12k0:
+                               flag = NM_IPAC_F_CHANM_CSD_NT_9k6;
+                               break;
+                       case RSL_CMOD_CSD_NT_14k5:
+                               flag = NM_IPAC_F_CHANM_CSD_NT_14k4;
+                               break;
+                       default:
+                               return true; /* unhandled NT rate */
+                       }
+               }
+               break;
+       default:
+               return true; /* unknown channel mode */
+       }
+
+       return (feat->val & flag) != 0;
+}
+
 static bool lchan_type_compat_with_mode(const struct gsm_lchan *lchan,
                                        const struct channel_mode_and_rate 
*ch_mode_rate)
 {
@@ -373,6 +453,8 @@

        switch (gsm48_chan_mode_to_non_vamos(chan_mode)) {
        case GSM48_CMODE_SIGN:
+               /* Signalling does not require a specific channel mode on the 
BTS,
+                * so skip the ipaccess feature check (below) and return 
directly. */
                switch (lchan->type) {
                case GSM_LCHAN_TCH_F: return chan_rate == CH_RATE_FULL;
                case GSM_LCHAN_TCH_H: return chan_rate == CH_RATE_HALF;
@@ -388,22 +470,39 @@
                 * an explicit override by the 'chan_rate' argument */
                switch (lchan->type) {
                case GSM_LCHAN_TCH_F:
-                       return chan_rate == CH_RATE_FULL;
+                       if (chan_rate != CH_RATE_FULL)
+                               return false;
+                       break;
                case GSM_LCHAN_TCH_H:
-                       return chan_rate == CH_RATE_HALF;
+                       if (chan_rate != CH_RATE_HALF)
+                               return false;
+                       break;
                default:
                        return false;
                }
+               break;

        case GSM48_CMODE_DATA_12k0:
        case GSM48_CMODE_DATA_14k5:
        case GSM48_CMODE_SPEECH_EFR:
                /* these services all explicitly require a TCH/F */
-               return lchan->type == GSM_LCHAN_TCH_F;
+               if (lchan->type != GSM_LCHAN_TCH_F)
+                       return false;
+               break;

        default:
                return false;
        }
+
+       switch (lchan->ts->trx->bts->type) {
+       case GSM_BTS_TYPE_NANOBTS:
+       case GSM_BTS_TYPE_OSMOBTS:
+               /* osmo-bts and nanoBTS report supported channel modes during
+                * the OML bring-up - additionally check them */
+               return ipacc_chan_mode_supported(lchan, ch_mode_rate);
+       default:
+               return true;
+       }
 }

 static __attribute__((constructor)) void assignment_fsm_init(void)

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

Gerrit-MessageType: newchange
Gerrit-Project: osmo-bsc
Gerrit-Branch: master
Gerrit-Change-Id: I680ba7993786f5486d671f931e75df4543670a37
Gerrit-Change-Number: 42590
Gerrit-PatchSet: 1
Gerrit-Owner: fixeria <[email protected]>

Reply via email to