Support proto IPAC_PROTO_EXT_PCU BSC<->PCU
Related: SYS#5303 Change-Id: I633db291107883c2e370a9b56606d562a990b714
This commit is contained in:
parent
8c29236d35
commit
1989a19066
|
@ -133,10 +133,12 @@ static void pcu_sock_close(int lost)
|
|||
|
||||
static int pcu_sock_read(struct osmo_fd *bfd)
|
||||
{
|
||||
struct gsm_pcu_if pcu_prim;
|
||||
const size_t max_len = sizeof(struct gsm_pcu_if) + 1000;
|
||||
uint8_t *buf = alloca(max_len);
|
||||
struct gsm_pcu_if *pcu_prim = (struct gsm_pcu_if *)buf;
|
||||
int rc;
|
||||
|
||||
rc = recv(bfd->fd, &pcu_prim, sizeof(pcu_prim), 0);
|
||||
rc = recv(bfd->fd, buf, max_len, 0);
|
||||
if (rc < 0 && errno == EAGAIN)
|
||||
return 0; /* Try again later */
|
||||
if (rc <= 0) {
|
||||
|
@ -144,7 +146,13 @@ static int pcu_sock_read(struct osmo_fd *bfd)
|
|||
return -EIO;
|
||||
}
|
||||
|
||||
return pcu_rx(pcu_prim.msg_type, &pcu_prim);
|
||||
if (rc < PCUIF_HDR_SIZE) {
|
||||
LOGP(DL1IF, LOGL_ERROR, "Received %d bytes on PCU Socket, but primitive "
|
||||
"hdr size is %zu, discarding\n", rc, PCUIF_HDR_SIZE);
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
return pcu_rx(pcu_prim, rc);
|
||||
}
|
||||
|
||||
static int pcu_sock_write(struct osmo_fd *bfd)
|
||||
|
|
|
@ -951,9 +951,32 @@ static int pcu_rx_app_info_req(struct gprs_rlcmac_bts *bts, struct gsm_pcu_if_ap
|
|||
return 0;
|
||||
}
|
||||
|
||||
int pcu_rx(uint8_t msg_type, struct gsm_pcu_if *pcu_prim)
|
||||
static int pcu_rx_container(struct gprs_rlcmac_bts *bts, struct gsm_pcu_if_container *container)
|
||||
{
|
||||
int rc;
|
||||
|
||||
switch (container->msg_type) {
|
||||
default:
|
||||
LOGP(DL1IF, LOGL_NOTICE, "(bts=%d) Rx unexpected msg type (%u) inside container!\n",
|
||||
bts->nr, container->msg_type);
|
||||
rc = -1;
|
||||
}
|
||||
return rc;
|
||||
}
|
||||
|
||||
#define CHECK_IF_MSG_SIZE(prim_len, prim_msg) \
|
||||
do { \
|
||||
size_t _len = PCUIF_HDR_SIZE + sizeof(prim_msg); \
|
||||
if (prim_len < _len) { \
|
||||
LOGP(DL1IF, LOGL_ERROR, "Received %zu bytes on PCU Socket, but primitive %s " \
|
||||
"size is %zu, discarding\n", prim_len, #prim_msg, _len); \
|
||||
return -EINVAL; \
|
||||
} \
|
||||
} while(0);
|
||||
int pcu_rx(struct gsm_pcu_if *pcu_prim, size_t pcu_prim_length)
|
||||
{
|
||||
int rc = 0;
|
||||
size_t exp_len;
|
||||
struct gprs_rlcmac_bts *bts = gprs_pcu_get_bts_by_nr(the_pcu, pcu_prim->bts_nr);
|
||||
if (!bts) {
|
||||
LOGP(DL1IF, LOGL_NOTICE, "Received message for new BTS%d\n", pcu_prim->bts_nr);
|
||||
|
@ -964,40 +987,59 @@ int pcu_rx(uint8_t msg_type, struct gsm_pcu_if *pcu_prim)
|
|||
}
|
||||
}
|
||||
|
||||
switch (msg_type) {
|
||||
switch (pcu_prim->msg_type) {
|
||||
case PCU_IF_MSG_DATA_IND:
|
||||
CHECK_IF_MSG_SIZE(pcu_prim_length, pcu_prim->u.data_ind);
|
||||
rc = pcu_rx_data_ind(bts, &pcu_prim->u.data_ind);
|
||||
break;
|
||||
case PCU_IF_MSG_DATA_CNF:
|
||||
CHECK_IF_MSG_SIZE(pcu_prim_length, pcu_prim->u.data_cnf);
|
||||
rc = pcu_rx_data_cnf(bts, &pcu_prim->u.data_cnf);
|
||||
break;
|
||||
case PCU_IF_MSG_RTS_REQ:
|
||||
CHECK_IF_MSG_SIZE(pcu_prim_length, pcu_prim->u.rts_req);
|
||||
rc = pcu_rx_rts_req(bts, &pcu_prim->u.rts_req);
|
||||
break;
|
||||
case PCU_IF_MSG_RACH_IND:
|
||||
CHECK_IF_MSG_SIZE(pcu_prim_length, pcu_prim->u.rach_ind);
|
||||
rc = pcu_rx_rach_ind(bts, &pcu_prim->u.rach_ind);
|
||||
break;
|
||||
case PCU_IF_MSG_INFO_IND:
|
||||
CHECK_IF_MSG_SIZE(pcu_prim_length, pcu_prim->u.info_ind);
|
||||
rc = pcu_rx_info_ind(bts, &pcu_prim->u.info_ind);
|
||||
break;
|
||||
case PCU_IF_MSG_TIME_IND:
|
||||
CHECK_IF_MSG_SIZE(pcu_prim_length, pcu_prim->u.time_ind);
|
||||
rc = pcu_rx_time_ind(bts, &pcu_prim->u.time_ind);
|
||||
break;
|
||||
case PCU_IF_MSG_PAG_REQ:
|
||||
CHECK_IF_MSG_SIZE(pcu_prim_length, pcu_prim->u.pag_req);
|
||||
rc = pcu_rx_pag_req(bts, &pcu_prim->u.pag_req);
|
||||
break;
|
||||
case PCU_IF_MSG_SUSP_REQ:
|
||||
CHECK_IF_MSG_SIZE(pcu_prim_length, pcu_prim->u.susp_req);
|
||||
rc = pcu_rx_susp_req(bts, &pcu_prim->u.susp_req);
|
||||
break;
|
||||
case PCU_IF_MSG_APP_INFO_REQ:
|
||||
CHECK_IF_MSG_SIZE(pcu_prim_length, pcu_prim->u.app_info_req);
|
||||
rc = pcu_rx_app_info_req(bts, &pcu_prim->u.app_info_req);
|
||||
break;
|
||||
case PCU_IF_MSG_INTERF_IND:
|
||||
/* TODO: handle interference reports */
|
||||
break;
|
||||
case PCU_IF_MSG_CONTAINER:
|
||||
CHECK_IF_MSG_SIZE(pcu_prim_length, pcu_prim->u.container);
|
||||
/* ^ check if we can access container fields, v check with container data length */
|
||||
exp_len = PCUIF_HDR_SIZE + sizeof(pcu_prim->u.container) + osmo_load16be(&pcu_prim->u.container.length);
|
||||
if (pcu_prim_length < exp_len) {
|
||||
LOGP(DL1IF, LOGL_ERROR, "Received %zu bytes on PCU Socket, but primitive container size" \
|
||||
"is %zu, discarding\n", pcu_prim_length, exp_len);
|
||||
}
|
||||
rc = pcu_rx_container(bts, &pcu_prim->u.container);
|
||||
break;
|
||||
default:
|
||||
LOGP(DL1IF, LOGL_ERROR, "Received unknown PCU msg type %d\n",
|
||||
msg_type);
|
||||
pcu_prim->msg_type);
|
||||
rc = -EINVAL;
|
||||
}
|
||||
|
||||
|
|
|
@ -160,7 +160,7 @@ extern "C" {
|
|||
#endif
|
||||
struct gprs_rlcmac_bts;
|
||||
|
||||
int pcu_rx(uint8_t msg_type, struct gsm_pcu_if *pcu_prim);
|
||||
int pcu_rx(struct gsm_pcu_if *pcu_prim, size_t pcu_prim_length);
|
||||
int pcu_l1if_open(void);
|
||||
void pcu_l1if_close(void);
|
||||
int pcu_sock_send(struct msgb *msg);
|
||||
|
@ -178,6 +178,9 @@ int pcu_rx_data_ind_pdtch(struct gprs_rlcmac_bts *bts, struct gprs_rlcmac_pdch *
|
|||
|
||||
void pcu_rx_block_time(struct gprs_rlcmac_bts *bts, uint16_t arfcn, uint32_t fn, uint8_t ts_no);
|
||||
uint16_t imsi2paging_group(const char* imsi);
|
||||
|
||||
#define PCUIF_HDR_SIZE ( sizeof(struct gsm_pcu_if) - sizeof(((struct gsm_pcu_if *)0)->u) )
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
|
|
@ -72,7 +72,7 @@ void test_pcu_rx_no_subscr_with_active_tbf()
|
|||
struct gsm_pcu_if pcu_prim = {PCU_IF_MSG_APP_INFO_REQ, };
|
||||
|
||||
fprintf(stderr, "--- %s ---\n", __func__);
|
||||
pcu_rx(PCU_IF_MSG_APP_INFO_REQ, &pcu_prim);
|
||||
pcu_rx(&pcu_prim, sizeof(struct gsm_pcu_if));
|
||||
fprintf(stderr, "\n");
|
||||
}
|
||||
|
||||
|
@ -106,7 +106,7 @@ void test_sched_app_info_ok(const struct gsm_pcu_if_app_info_req *req)
|
|||
|
||||
fprintf(stderr, "--- %s ---\n", __func__);
|
||||
pcu_prim.u.app_info_req = *req;
|
||||
pcu_rx(PCU_IF_MSG_APP_INFO_REQ, &pcu_prim);
|
||||
pcu_rx(&pcu_prim, sizeof(struct gsm_pcu_if));
|
||||
|
||||
msg = sched_app_info(tbf1);
|
||||
assert(msg);
|
||||
|
@ -126,7 +126,7 @@ void test_sched_app_info_missing_app_info_in_bts(const struct gsm_pcu_if_app_inf
|
|||
|
||||
fprintf(stderr, "--- %s ---\n", __func__);
|
||||
pcu_prim.u.app_info_req = *req;
|
||||
pcu_rx(PCU_IF_MSG_APP_INFO_REQ, &pcu_prim);
|
||||
pcu_rx(&pcu_prim, sizeof(struct gsm_pcu_if));
|
||||
|
||||
msgb_free(bts->app_info);
|
||||
bts->app_info = NULL;
|
||||
|
@ -142,8 +142,8 @@ void test_pcu_rx_overwrite_app_info(const struct gsm_pcu_if_app_info_req *req)
|
|||
|
||||
fprintf(stderr, "--- %s ---\n", __func__);
|
||||
pcu_prim.u.app_info_req = *req;
|
||||
pcu_rx(PCU_IF_MSG_APP_INFO_REQ, &pcu_prim);
|
||||
pcu_rx(PCU_IF_MSG_APP_INFO_REQ, &pcu_prim);
|
||||
pcu_rx(&pcu_prim, sizeof(struct gsm_pcu_if));
|
||||
pcu_rx(&pcu_prim, sizeof(struct gsm_pcu_if));
|
||||
fprintf(stderr, "\n");
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in New Issue