<p>laforge <strong>submitted</strong> this change.</p><p><a href="https://gerrit.osmocom.org/c/osmo-bts/+/24619">View Change</a></p><div style="white-space:pre-wrap">Approvals:
  laforge: Looks good to me, approved
  Jenkins Builder: Verified

</div><pre style="font-family: monospace,monospace; white-space: pre-wrap;">Support forwarding proto IPAC_PROTO_EXT_PCU BSC<->PCU<br><br>This new extension protocol is used to forward Osmocom PCUIF messages<br>BSC<->BTS<->PCU.<br>It will be sent re-using the IPA multiplex of the OML link between<br>BSC and BTS. BTS is responsible for forwarding the message over the unix<br>socket to the PCU.<br><br>PCUIF existing RX path needs to be reworked in order to accept<br>variable-size messages, in order to be able to transparently forward<br>messages without knowing about them (the new container message is<br>variable-length).<br><br>Related: SYS#5303<br>Change-Id: I73fdb17107494ade9263a62d1f729e67303fce87<br>---<br>M include/osmo-bts/Makefile.am<br>A include/osmo-bts/abis_osmo.h<br>M include/osmo-bts/bts.h<br>M include/osmo-bts/pcu_if.h<br>M src/common/Makefile.am<br>M src/common/abis.c<br>A src/common/abis_osmo.c<br>M src/common/bts.c<br>M src/common/pcu_sock.c<br>9 files changed, 201 insertions(+), 10 deletions(-)<br><br></pre><pre style="font-family: monospace,monospace; white-space: pre-wrap;"><span>diff --git a/include/osmo-bts/Makefile.am b/include/osmo-bts/Makefile.am</span><br><span>index 84dc667..d52c9aa 100644</span><br><span>--- a/include/osmo-bts/Makefile.am</span><br><span>+++ b/include/osmo-bts/Makefile.am</span><br><span>@@ -1,5 +1,6 @@</span><br><span> noinst_HEADERS = \</span><br><span>   abis.h \</span><br><span style="color: hsl(120, 100%, 40%);">+      abis_osmo.h \</span><br><span>        bts.h \</span><br><span>      bts_model.h \</span><br><span>        bts_shutdown_fsm.h \</span><br><span>diff --git a/include/osmo-bts/abis_osmo.h b/include/osmo-bts/abis_osmo.h</span><br><span>new file mode 100644</span><br><span>index 0000000..be2817f</span><br><span>--- /dev/null</span><br><span>+++ b/include/osmo-bts/abis_osmo.h</span><br><span>@@ -0,0 +1,10 @@</span><br><span style="color: hsl(120, 100%, 40%);">+#pragma once</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+#include <osmocom/core/msgb.h></span><br><span style="color: hsl(120, 100%, 40%);">+#include <osmo-bts/pcuif_proto.h></span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+struct gsm_bts;</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+int down_osmo(struct gsm_bts *bts, struct msgb *msg);</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+int abis_osmo_pcu_tx_container(struct gsm_bts *bts, const struct gsm_pcu_if_container *container);</span><br><span>diff --git a/include/osmo-bts/bts.h b/include/osmo-bts/bts.h</span><br><span>index 978a548..a891fb7 100644</span><br><span>--- a/include/osmo-bts/bts.h</span><br><span>+++ b/include/osmo-bts/bts.h</span><br><span>@@ -167,6 +167,8 @@</span><br><span>  /* how do we talk OML with this TRX? */</span><br><span>      struct e1inp_sign_link *oml_link;</span><br><span>    struct timespec oml_conn_established_timestamp;</span><br><span style="color: hsl(120, 100%, 40%);">+       /* OSMO extenion link associated to same line as oml_link: */</span><br><span style="color: hsl(120, 100%, 40%);">+ struct e1inp_sign_link *osmo_link;</span><br><span> </span><br><span>       /* Abis network management O&M handle */</span><br><span>         struct gsm_abis_mo mo;</span><br><span>diff --git a/include/osmo-bts/pcu_if.h b/include/osmo-bts/pcu_if.h</span><br><span>index 6ef8dc5..12a8abc 100644</span><br><span>--- a/include/osmo-bts/pcu_if.h</span><br><span>+++ b/include/osmo-bts/pcu_if.h</span><br><span>@@ -1,8 +1,12 @@</span><br><span> #ifndef _PCU_IF_H</span><br><span> #define _PCU_IF_H</span><br><span> </span><br><span style="color: hsl(120, 100%, 40%);">+#include <osmo-bts/pcuif_proto.h></span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span> extern int pcu_direct;</span><br><span> </span><br><span style="color: hsl(120, 100%, 40%);">+#define PCUIF_HDR_SIZE ( sizeof(struct gsm_pcu_if) - sizeof(((struct gsm_pcu_if *)0)->u) )</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span> int pcu_tx_info_ind(void);</span><br><span> int pcu_tx_si(const struct gsm_bts *bts, enum osmo_sysinfo_type si_type, bool enable);</span><br><span> int pcu_tx_app_info_req(struct gsm_bts *bts, uint8_t app_type, uint8_t len, const uint8_t *app_data);</span><br><span>@@ -20,6 +24,7 @@</span><br><span> int pcu_tx_pag_req(const uint8_t *identity_lv, uint8_t chan_needed);</span><br><span> int pcu_tx_pch_data_cnf(uint32_t fn, uint8_t *data, uint8_t len);</span><br><span> int pcu_tx_susp_req(struct gsm_lchan *lchan, uint32_t tlli, const uint8_t *ra_id, uint8_t cause);</span><br><span style="color: hsl(120, 100%, 40%);">+int pcu_sock_send(struct gsm_network *net, struct msgb *msg);</span><br><span> </span><br><span> int pcu_sock_init(const char *path);</span><br><span> void pcu_sock_exit(void);</span><br><span>diff --git a/src/common/Makefile.am b/src/common/Makefile.am</span><br><span>index d979bc0..72438c6 100644</span><br><span>--- a/src/common/Makefile.am</span><br><span>+++ b/src/common/Makefile.am</span><br><span>@@ -12,6 +12,7 @@</span><br><span>   sysinfo.c \</span><br><span>  logging.c \</span><br><span>  abis.c \</span><br><span style="color: hsl(120, 100%, 40%);">+      abis_osmo.c \</span><br><span>        oml.c \</span><br><span>      bts.c \</span><br><span>      bts_trx.c \</span><br><span>diff --git a/src/common/abis.c b/src/common/abis.c</span><br><span>index 17a244c..abef826 100644</span><br><span>--- a/src/common/abis.c</span><br><span>+++ b/src/common/abis.c</span><br><span>@@ -48,6 +48,7 @@</span><br><span> #include <osmo-bts/bts.h></span><br><span> #include <osmo-bts/rsl.h></span><br><span> #include <osmo-bts/oml.h></span><br><span style="color: hsl(120, 100%, 40%);">+#include <osmo-bts/abis_osmo.h></span><br><span> #include <osmo-bts/bts_model.h></span><br><span> #include <osmo-bts/bts_trx.h></span><br><span> </span><br><span>@@ -113,6 +114,8 @@</span><br><span>           if (clock_gettime(CLOCK_MONOTONIC, &g_bts->oml_conn_established_timestamp) != 0)</span><br><span>                      memset(&g_bts->oml_conn_established_timestamp, 0,</span><br><span>                            sizeof(g_bts->oml_conn_established_timestamp));</span><br><span style="color: hsl(120, 100%, 40%);">+             g_bts->osmo_link = e1inp_sign_link_create(sign_ts, E1INP_SIGN_OSMO,</span><br><span style="color: hsl(120, 100%, 40%);">+                                                          g_bts->c0, IPAC_PROTO_OSMO, 0);</span><br><span>                 drain_oml_queue(g_bts);</span><br><span>              bts_link_estab(g_bts);</span><br><span>               return g_bts->oml_link;</span><br><span>@@ -158,10 +161,15 @@</span><br><span>                   "A common error is a mismatch between unit_id configuration parameters of BTS and BSC.\n",</span><br><span>                         (uint64_t)(now.tv_sec - g_bts->oml_conn_established_timestamp.tv_sec));</span><br><span>           }</span><br><span style="color: hsl(120, 100%, 40%);">+             g_bts->oml_link = NULL;</span><br><span>   }</span><br><span style="color: hsl(0, 100%, 40%);">-       g_bts->oml_link = NULL;</span><br><span>   memset(&g_bts->oml_conn_established_timestamp, 0, sizeof(g_bts->oml_conn_established_timestamp));</span><br><span> </span><br><span style="color: hsl(120, 100%, 40%);">+       if (g_bts->osmo_link) {</span><br><span style="color: hsl(120, 100%, 40%);">+            e1inp_sign_link_destroy(g_bts->osmo_link);</span><br><span style="color: hsl(120, 100%, 40%);">+         g_bts->osmo_link = NULL;</span><br><span style="color: hsl(120, 100%, 40%);">+   }</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span>  /* Then iterate over the RSL signalling links */</span><br><span>     llist_for_each_entry(trx, &g_bts->trx_list, list) {</span><br><span>           if (trx->rsl_link) {</span><br><span>@@ -191,6 +199,9 @@</span><br><span>        case E1INP_SIGN_RSL:</span><br><span>                 down_rsl(link->trx, msg);</span><br><span>                 break;</span><br><span style="color: hsl(120, 100%, 40%);">+        case E1INP_SIGN_OSMO:</span><br><span style="color: hsl(120, 100%, 40%);">+         down_osmo(link->trx->bts, msg);</span><br><span style="color: hsl(120, 100%, 40%);">+         break;</span><br><span>       default:</span><br><span>             msgb_free(msg);</span><br><span>              break;</span><br><span>diff --git a/src/common/abis_osmo.c b/src/common/abis_osmo.c</span><br><span>new file mode 100644</span><br><span>index 0000000..46dc5fa</span><br><span>--- /dev/null</span><br><span>+++ b/src/common/abis_osmo.c</span><br><span>@@ -0,0 +1,136 @@</span><br><span style="color: hsl(120, 100%, 40%);">+/* OSMO extenion link associated to same line as oml_link: */</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+/* (C) 2021 by sysmocom - s.m.f.c. GmbH <info@sysmocom.de></span><br><span style="color: hsl(120, 100%, 40%);">+ * Author: Pau Espin Pedrol <pespin@sysmocom.de></span><br><span style="color: hsl(120, 100%, 40%);">+ *</span><br><span style="color: hsl(120, 100%, 40%);">+ * All Rights Reserved</span><br><span style="color: hsl(120, 100%, 40%);">+ *</span><br><span style="color: hsl(120, 100%, 40%);">+ * This program is free software; you can redistribute it and/or modify</span><br><span style="color: hsl(120, 100%, 40%);">+ * it under the terms of the GNU Affero General Public License as published by</span><br><span style="color: hsl(120, 100%, 40%);">+ * the Free Software Foundation; either version 3 of the License, or</span><br><span style="color: hsl(120, 100%, 40%);">+ * (at your option) any later version.</span><br><span style="color: hsl(120, 100%, 40%);">+ *</span><br><span style="color: hsl(120, 100%, 40%);">+ * This program is distributed in the hope that it will be useful,</span><br><span style="color: hsl(120, 100%, 40%);">+ * but WITHOUT ANY WARRANTY; without even the implied warranty of</span><br><span style="color: hsl(120, 100%, 40%);">+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the</span><br><span style="color: hsl(120, 100%, 40%);">+ * GNU General Public License for more details.</span><br><span style="color: hsl(120, 100%, 40%);">+ *</span><br><span style="color: hsl(120, 100%, 40%);">+ * You should have received a copy of the GNU Affero General Public License</span><br><span style="color: hsl(120, 100%, 40%);">+ * along with this program.  If not, see <http://www.gnu.org/licenses/>.</span><br><span style="color: hsl(120, 100%, 40%);">+ *</span><br><span style="color: hsl(120, 100%, 40%);">+ */</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+#include <errno.h></span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+#include <osmocom/core/msgb.h></span><br><span style="color: hsl(120, 100%, 40%);">+#include <osmocom/gsm/ipa.h></span><br><span style="color: hsl(120, 100%, 40%);">+#include <osmocom/gsm/protocol/ipaccess.h></span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+#include <osmo-bts/bts.h></span><br><span style="color: hsl(120, 100%, 40%);">+#include <osmo-bts/logging.h></span><br><span style="color: hsl(120, 100%, 40%);">+#include <osmo-bts/pcu_if.h></span><br><span style="color: hsl(120, 100%, 40%);">+#include <osmo-bts/pcuif_proto.h></span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+extern struct gsm_network bts_gsmnet;</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+#define OM_HEADROOM_SIZE  128</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+////////////////////////////////////////</span><br><span style="color: hsl(120, 100%, 40%);">+// OSMO ABIS extensions (PCU)</span><br><span style="color: hsl(120, 100%, 40%);">+///////////////////////////////////////</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+static struct msgb *abis_osmo_pcu_msgb_alloc(uint8_t msg_type, uint8_t bts_nr, size_t extra_size)</span><br><span style="color: hsl(120, 100%, 40%);">+{</span><br><span style="color: hsl(120, 100%, 40%);">+       struct msgb *msg;</span><br><span style="color: hsl(120, 100%, 40%);">+     struct gsm_pcu_if *pcu_prim;</span><br><span style="color: hsl(120, 100%, 40%);">+  msg = msgb_alloc_headroom(OM_HEADROOM_SIZE + sizeof(struct gsm_pcu_if) + extra_size,</span><br><span style="color: hsl(120, 100%, 40%);">+                            OM_HEADROOM_SIZE, "IPA/ABIS/OSMO");</span><br><span style="color: hsl(120, 100%, 40%);">+       /* Only header is filled, caller is responible for reserving + filling</span><br><span style="color: hsl(120, 100%, 40%);">+         * message type specific contents: */</span><br><span style="color: hsl(120, 100%, 40%);">+ msgb_put(msg, PCUIF_HDR_SIZE);</span><br><span style="color: hsl(120, 100%, 40%);">+        pcu_prim = (struct gsm_pcu_if *) msgb_data(msg);</span><br><span style="color: hsl(120, 100%, 40%);">+      pcu_prim->msg_type = msg_type;</span><br><span style="color: hsl(120, 100%, 40%);">+     pcu_prim->bts_nr = bts_nr;</span><br><span style="color: hsl(120, 100%, 40%);">+ return msg;</span><br><span style="color: hsl(120, 100%, 40%);">+}</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+/* Send a OML NM Message from BSC to BTS */</span><br><span style="color: hsl(120, 100%, 40%);">+int abis_osmo_sendmsg(struct gsm_bts *bts, struct msgb *msg)</span><br><span style="color: hsl(120, 100%, 40%);">+{</span><br><span style="color: hsl(120, 100%, 40%);">+        msg->dst = bts->osmo_link;</span><br><span style="color: hsl(120, 100%, 40%);">+      msg->l2h = msg->data;</span><br><span style="color: hsl(120, 100%, 40%);">+   return abis_sendmsg(msg);</span><br><span style="color: hsl(120, 100%, 40%);">+}</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+/* Send IPA/OSMO/PCU extension Abis message from PCU to BSC */</span><br><span style="color: hsl(120, 100%, 40%);">+static int abis_osmo_pcu_sendmsg(struct gsm_bts *bts, struct msgb *msg)</span><br><span style="color: hsl(120, 100%, 40%);">+{</span><br><span style="color: hsl(120, 100%, 40%);">+  ipa_prepend_header_ext(msg, IPAC_PROTO_EXT_PCU);</span><br><span style="color: hsl(120, 100%, 40%);">+      return abis_osmo_sendmsg(bts, msg);</span><br><span style="color: hsl(120, 100%, 40%);">+}</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+int abis_osmo_pcu_tx_container(struct gsm_bts *bts, const struct gsm_pcu_if_container *container)</span><br><span style="color: hsl(120, 100%, 40%);">+{</span><br><span style="color: hsl(120, 100%, 40%);">+        uint16_t data_length = osmo_load16be(&container->length);</span><br><span style="color: hsl(120, 100%, 40%);">+      struct msgb *msg = abis_osmo_pcu_msgb_alloc(PCU_IF_MSG_CONTAINER, bts->nr, data_length);</span><br><span style="color: hsl(120, 100%, 40%);">+   struct gsm_pcu_if *pcu_prim = (struct gsm_pcu_if *) msgb_data(msg);</span><br><span style="color: hsl(120, 100%, 40%);">+   struct gsm_pcu_if_container *tx_cont = &pcu_prim->u.container;</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+       msgb_put(msg, sizeof(*tx_cont) + data_length);</span><br><span style="color: hsl(120, 100%, 40%);">+        tx_cont->msg_type = container->msg_type;</span><br><span style="color: hsl(120, 100%, 40%);">+        tx_cont->length = container->length;</span><br><span style="color: hsl(120, 100%, 40%);">+    if (data_length)</span><br><span style="color: hsl(120, 100%, 40%);">+              memcpy(tx_cont->data, container->data, data_length);</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+  return abis_osmo_pcu_sendmsg(bts, msg);</span><br><span style="color: hsl(120, 100%, 40%);">+}</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+/* incoming IPA/OSMOEXT/PCU Abis message from BSC */</span><br><span style="color: hsl(120, 100%, 40%);">+static int rx_down_osmo_pcu(struct gsm_bts *bts, struct msgb *msg)</span><br><span style="color: hsl(120, 100%, 40%);">+{</span><br><span style="color: hsl(120, 100%, 40%);">+   struct gsm_pcu_if *pcu_prim;</span><br><span style="color: hsl(120, 100%, 40%);">+  if (msgb_l2len(msg) < PCUIF_HDR_SIZE) {</span><br><span style="color: hsl(120, 100%, 40%);">+            LOGP(DPCU, LOGL_ERROR, "ABIS_OSMO_PCU message too short\n");</span><br><span style="color: hsl(120, 100%, 40%);">+                oml_tx_failure_event_rep(&bts->mo, NM_SEVER_MAJOR, OSMO_EVT_MAJ_UKWN_MSG,</span><br><span style="color: hsl(120, 100%, 40%);">+                                       "ABIS_OSMO_PCU message too short\n");</span><br><span style="color: hsl(120, 100%, 40%);">+              msgb_free(msg);</span><br><span style="color: hsl(120, 100%, 40%);">+               return -EIO;</span><br><span style="color: hsl(120, 100%, 40%);">+  }</span><br><span style="color: hsl(120, 100%, 40%);">+     pcu_prim = msgb_l2(msg);</span><br><span style="color: hsl(120, 100%, 40%);">+      LOGP(DPCU, LOGL_INFO, "Rx BSC->BTS%d ABIS_OSMO_PCU msg type %u\n",</span><br><span style="color: hsl(120, 100%, 40%);">+            pcu_prim->bts_nr, pcu_prim->msg_type);</span><br><span style="color: hsl(120, 100%, 40%);">+     /* we patch the bts_nr received from BTS with the bts_nr we used to set up in the local PCU */</span><br><span style="color: hsl(120, 100%, 40%);">+        pcu_prim->bts_nr = bts->nr;</span><br><span style="color: hsl(120, 100%, 40%);">+     /* Trim Abis lower layers: */</span><br><span style="color: hsl(120, 100%, 40%);">+ msgb_pull_to_l2(msg);</span><br><span style="color: hsl(120, 100%, 40%);">+ /* we simply forward it to PCUIF: */</span><br><span style="color: hsl(120, 100%, 40%);">+  return pcu_sock_send(&bts_gsmnet, msg);</span><br><span style="color: hsl(120, 100%, 40%);">+}</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+/* incoming IPA/OSMO extension Abis message from BSC */</span><br><span style="color: hsl(120, 100%, 40%);">+int down_osmo(struct gsm_bts *bts, struct msgb *msg)</span><br><span style="color: hsl(120, 100%, 40%);">+{</span><br><span style="color: hsl(120, 100%, 40%);">+    uint8_t *type;</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+      if (msgb_l2len(msg) < 1) {</span><br><span style="color: hsl(120, 100%, 40%);">+         oml_tx_failure_event_rep(&bts->mo, NM_SEVER_MAJOR, OSMO_EVT_MAJ_UKWN_MSG,</span><br><span style="color: hsl(120, 100%, 40%);">+                                       "OSMO message too short\n");</span><br><span style="color: hsl(120, 100%, 40%);">+               msgb_free(msg);</span><br><span style="color: hsl(120, 100%, 40%);">+               return -EIO;</span><br><span style="color: hsl(120, 100%, 40%);">+  }</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+   type = msgb_l2(msg);</span><br><span style="color: hsl(120, 100%, 40%);">+  msg->l2h = type + 1;</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+     switch (*type) {</span><br><span style="color: hsl(120, 100%, 40%);">+      case IPAC_PROTO_EXT_PCU:</span><br><span style="color: hsl(120, 100%, 40%);">+              return rx_down_osmo_pcu(bts, msg);</span><br><span style="color: hsl(120, 100%, 40%);">+    default:</span><br><span style="color: hsl(120, 100%, 40%);">+              oml_tx_failure_event_rep(&bts->mo, NM_SEVER_MAJOR, OSMO_EVT_MAJ_UKWN_MSG,</span><br><span style="color: hsl(120, 100%, 40%);">+                                       "OSMO message unknown extension %u\n", *type);</span><br><span style="color: hsl(120, 100%, 40%);">+             msgb_free(msg);</span><br><span style="color: hsl(120, 100%, 40%);">+               return -EIO;</span><br><span style="color: hsl(120, 100%, 40%);">+  }</span><br><span style="color: hsl(120, 100%, 40%);">+}</span><br><span>diff --git a/src/common/bts.c b/src/common/bts.c</span><br><span>index bf29113..7d5732b 100644</span><br><span>--- a/src/common/bts.c</span><br><span>+++ b/src/common/bts.c</span><br><span>@@ -371,6 +371,7 @@</span><br><span>      /* features implemented in 'common', available for all models */</span><br><span>     osmo_bts_set_feature(bts->features, BTS_FEAT_ETWS_PN);</span><br><span>    osmo_bts_set_feature(bts->features, BTS_FEAT_IPV6_NSVC);</span><br><span style="color: hsl(120, 100%, 40%);">+   osmo_bts_set_feature(bts->features, BTS_FEAT_ABIS_OSMO_PCU);</span><br><span> </span><br><span>  rc = bts_model_init(bts);</span><br><span>    if (rc < 0) {</span><br><span>diff --git a/src/common/pcu_sock.c b/src/common/pcu_sock.c</span><br><span>index 5a04bf0..f40dd42 100644</span><br><span>--- a/src/common/pcu_sock.c</span><br><span>+++ b/src/common/pcu_sock.c</span><br><span>@@ -45,6 +45,7 @@</span><br><span> #include <osmo-bts/signal.h></span><br><span> #include <osmo-bts/l1sap.h></span><br><span> #include <osmo-bts/oml.h></span><br><span style="color: hsl(120, 100%, 40%);">+#include <osmo-bts/abis_osmo.h></span><br><span> </span><br><span> uint32_t trx_get_hlayer1(const struct gsm_bts_trx *trx);</span><br><span> </span><br><span>@@ -62,8 +63,6 @@</span><br><span>   [PCU_IF_SAPI_PTCCH] =   "PTCCH",</span><br><span> };</span><br><span> </span><br><span style="color: hsl(0, 100%, 40%);">-static int pcu_sock_send(struct gsm_network *net, struct msgb *msg);</span><br><span style="color: hsl(0, 100%, 40%);">-</span><br><span> /*</span><br><span>  * PCU messages</span><br><span>  */</span><br><span>@@ -884,11 +883,21 @@</span><br><span>     return 0;</span><br><span> }</span><br><span> </span><br><span style="color: hsl(120, 100%, 40%);">+#define CHECK_IF_MSG_SIZE(prim_len, prim_msg) \</span><br><span style="color: hsl(120, 100%, 40%);">+   do { \</span><br><span style="color: hsl(120, 100%, 40%);">+                size_t _len = PCUIF_HDR_SIZE + sizeof(prim_msg); \</span><br><span style="color: hsl(120, 100%, 40%);">+            if (prim_len < _len) { \</span><br><span style="color: hsl(120, 100%, 40%);">+                   LOGP(DPCU, LOGL_ERROR, "Received %zu bytes on PCU Socket, but primitive %s " \</span><br><span style="color: hsl(120, 100%, 40%);">+                           "size is %zu, discarding\n", prim_len, #prim_msg, _len); \</span><br><span style="color: hsl(120, 100%, 40%);">+                     return -EINVAL; \</span><br><span style="color: hsl(120, 100%, 40%);">+             } \</span><br><span style="color: hsl(120, 100%, 40%);">+   } while(0);</span><br><span> static int pcu_rx(struct gsm_network *net, uint8_t msg_type,</span><br><span style="color: hsl(0, 100%, 40%);">-     struct gsm_pcu_if *pcu_prim)</span><br><span style="color: hsl(120, 100%, 40%);">+  struct gsm_pcu_if *pcu_prim, size_t prim_len)</span><br><span> {</span><br><span>   int rc = 0;</span><br><span>  struct gsm_bts *bts;</span><br><span style="color: hsl(120, 100%, 40%);">+  size_t exp_len;</span><br><span> </span><br><span>  if ((bts = gsm_bts_num(net, pcu_prim->bts_nr)) == NULL) {</span><br><span>                 LOGP(DPCU, LOGL_ERROR, "Received PCU Prim for non-existent BTS %u\n", pcu_prim->bts_nr);</span><br><span>@@ -897,17 +906,32 @@</span><br><span> </span><br><span>    switch (msg_type) {</span><br><span>  case PCU_IF_MSG_DATA_REQ:</span><br><span style="color: hsl(120, 100%, 40%);">+             CHECK_IF_MSG_SIZE(prim_len, pcu_prim->u.data_req);</span><br><span>                rc = pcu_rx_data_req(bts, msg_type, &pcu_prim->u.data_req);</span><br><span>           break;</span><br><span>       case PCU_IF_MSG_PAG_REQ:</span><br><span style="color: hsl(120, 100%, 40%);">+              CHECK_IF_MSG_SIZE(prim_len, pcu_prim->u.pag_req);</span><br><span>                 rc = pcu_rx_pag_req(bts, msg_type, &pcu_prim->u.pag_req);</span><br><span>             break;</span><br><span>       case PCU_IF_MSG_ACT_REQ:</span><br><span style="color: hsl(120, 100%, 40%);">+              CHECK_IF_MSG_SIZE(prim_len, pcu_prim->u.act_req);</span><br><span>                 rc = pcu_rx_act_req(bts, &pcu_prim->u.act_req);</span><br><span>               break;</span><br><span>       case PCU_IF_MSG_TXT_IND:</span><br><span style="color: hsl(120, 100%, 40%);">+              CHECK_IF_MSG_SIZE(prim_len, pcu_prim->u.txt_ind);</span><br><span>                 rc = pcu_rx_txt_ind(bts, &pcu_prim->u.txt_ind);</span><br><span>               break;</span><br><span style="color: hsl(120, 100%, 40%);">+        case PCU_IF_MSG_CONTAINER:</span><br><span style="color: hsl(120, 100%, 40%);">+            CHECK_IF_MSG_SIZE(prim_len, pcu_prim->u.container);</span><br><span style="color: hsl(120, 100%, 40%);">+                /* ^ check if we can access container fields, v check with container data length */</span><br><span style="color: hsl(120, 100%, 40%);">+           exp_len = PCUIF_HDR_SIZE + sizeof(pcu_prim->u.container) + osmo_load16be(&pcu_prim->u.container.length);</span><br><span style="color: hsl(120, 100%, 40%);">+            if (prim_len < exp_len) {</span><br><span style="color: hsl(120, 100%, 40%);">+                  LOGP(DPCU, LOGL_ERROR, "Received %zu bytes on PCU Socket, but primitive "</span><br><span style="color: hsl(120, 100%, 40%);">+                        "container size is %zu, discarding\n", prim_len, exp_len);</span><br><span style="color: hsl(120, 100%, 40%);">+                     return -EINVAL;</span><br><span style="color: hsl(120, 100%, 40%);">+               }</span><br><span style="color: hsl(120, 100%, 40%);">+             rc = abis_osmo_pcu_tx_container(bts, &pcu_prim->u.container);</span><br><span style="color: hsl(120, 100%, 40%);">+          break;</span><br><span>       default:</span><br><span>             LOGP(DPCU, LOGL_ERROR, "Received unknown PCU msg type %d\n",</span><br><span>                       msg_type);</span><br><span>@@ -928,7 +952,7 @@</span><br><span>     struct llist_head upqueue;      /* queue for sending messages */</span><br><span> };</span><br><span> </span><br><span style="color: hsl(0, 100%, 40%);">-static int pcu_sock_send(struct gsm_network *net, struct msgb *msg)</span><br><span style="color: hsl(120, 100%, 40%);">+int pcu_sock_send(struct gsm_network *net, struct msgb *msg)</span><br><span> {</span><br><span>     struct pcu_sock_state *state = net->pcu_state;</span><br><span>    struct osmo_fd *conn_bfd;</span><br><span>@@ -1019,7 +1043,7 @@</span><br><span>    struct msgb *msg;</span><br><span>    int rc;</span><br><span> </span><br><span style="color: hsl(0, 100%, 40%);">-     msg = msgb_alloc(sizeof(*pcu_prim), "pcu_sock_rx");</span><br><span style="color: hsl(120, 100%, 40%);">+ msg = msgb_alloc(sizeof(*pcu_prim) + 1000, "pcu_sock_rx");</span><br><span>         if (!msg)</span><br><span>            return -ENOMEM;</span><br><span> </span><br><span>@@ -1037,14 +1061,14 @@</span><br><span>                goto close;</span><br><span>  }</span><br><span> </span><br><span style="color: hsl(0, 100%, 40%);">-   if (rc < sizeof(*pcu_prim)) {</span><br><span style="color: hsl(0, 100%, 40%);">-                LOGP(DPCU, LOGL_ERROR, "Received %d bytes on PCU Socket, but primitive size "</span><br><span style="color: hsl(0, 100%, 40%);">-              "is %zu, discarding\n", rc, sizeof(*pcu_prim));</span><br><span style="color: hsl(120, 100%, 40%);">+        if (rc < PCUIF_HDR_SIZE) {</span><br><span style="color: hsl(120, 100%, 40%);">+         LOGP(DPCU, LOGL_ERROR, "Received %d bytes on PCU Socket, but primitive hdr size "</span><br><span style="color: hsl(120, 100%, 40%);">+                "is %zu, discarding\n", rc, PCUIF_HDR_SIZE);</span><br><span>          msgb_free(msg);</span><br><span>              return 0;</span><br><span>    }</span><br><span> </span><br><span style="color: hsl(0, 100%, 40%);">-   rc = pcu_rx(state->net, pcu_prim->msg_type, pcu_prim);</span><br><span style="color: hsl(120, 100%, 40%);">+  rc = pcu_rx(state->net, pcu_prim->msg_type, pcu_prim, rc);</span><br><span> </span><br><span>         /* as we always synchronously process the message in pcu_rx() and</span><br><span>     * its callbacks, we can free the message here. */</span><br><span></span><br></pre><p>To view, visit <a href="https://gerrit.osmocom.org/c/osmo-bts/+/24619">change 24619</a>. To unsubscribe, or for help writing mail filters, visit <a href="https://gerrit.osmocom.org/settings">settings</a>.</p><div itemscope itemtype="http://schema.org/EmailMessage"><div itemscope itemprop="action" itemtype="http://schema.org/ViewAction"><link itemprop="url" href="https://gerrit.osmocom.org/c/osmo-bts/+/24619"/><meta itemprop="name" content="View Change"/></div></div>

<div style="display:none"> Gerrit-Project: osmo-bts </div>
<div style="display:none"> Gerrit-Branch: master </div>
<div style="display:none"> Gerrit-Change-Id: I73fdb17107494ade9263a62d1f729e67303fce87 </div>
<div style="display:none"> Gerrit-Change-Number: 24619 </div>
<div style="display:none"> Gerrit-PatchSet: 7 </div>
<div style="display:none"> Gerrit-Owner: pespin <pespin@sysmocom.de> </div>
<div style="display:none"> Gerrit-Reviewer: Jenkins Builder </div>
<div style="display:none"> Gerrit-Reviewer: laforge <laforge@osmocom.org> </div>
<div style="display:none"> Gerrit-MessageType: merged </div>