From holger at freyther.de Tue Jul 22 10:01:03 2014 From: holger at freyther.de (Holger Hans Peter Freyther) Date: Tue, 22 Jul 2014 12:01:03 +0200 Subject: [PATCH] use osmocom auth API instead of direct calls In-Reply-To: <1401898914-23556-1-git-send-email-Max.Suraev@fairwaves.co> References: <1401898914-23556-1-git-send-email-Max.Suraev@fairwaves.co> Message-ID: <20140722100103.GA14416@xiaoyu.lan> On Wed, Jun 04, 2014 at 06:21:54PM +0200, Max Suraev wrote: Hi! sorry for the late reply (and I also intend to reply for reviving our wednesday meetings. I could talk about TCAP/MAP..) > --- > openbsc/src/libmsc/auth.c | 68 +++++++++++++++++++---------------------------- > 1 file changed, 28 insertions(+), 40 deletions(-) > > diff --git a/openbsc/src/libmsc/auth.c b/openbsc/src/libmsc/auth.c > index 10d8edf..ab84975 100644 > --- a/openbsc/src/libmsc/auth.c > +++ b/openbsc/src/libmsc/auth.c > @@ -25,46 +25,11 @@ > #include > #include > > -#include > +#include > > #include > > > -static int > -_use_xor(struct gsm_auth_info *ainfo, struct gsm_auth_tuple *atuple) > -{ > - > - for (i=0; i<4; i++) > - atuple->sres[i] = atuple->rand[i] ^ ainfo->a3a8_ki[i]; > - for (i=4; i<12; i++) > - atuple->kc[i-4] = atuple->rand[i] ^ ainfo->a3a8_ki[i]; > - > - return 0; > -} > - > -static int > -_use_comp128_v1(struct gsm_auth_info *ainfo, struct gsm_auth_tuple *atuple) > -{ > - if (ainfo->a3a8_ki_len != A38_COMP128_KEY_LEN) { > - LOGP(DMM, LOGL_ERROR, "Invalid COMP128v1 key (len=%d) %s\n", > - ainfo->a3a8_ki_len, > - osmo_hexdump(ainfo->a3a8_ki, ainfo->a3a8_ki_len)); > - return -1; > - } > - > - comp128(ainfo->a3a8_ki, atuple->rand, atuple->sres, atuple->kc); > - > - return 0; > -} > - > /* Return values > * -1 -> Internal error > * 0 -> Not available > @@ -76,6 +41,11 @@ int auth_get_tuple_for_subscr(struct gsm_auth_tuple *atuple, > { > struct gsm_auth_info ainfo; > int i, rc; > + static struct osmo_sub_auth_data auth = { > + .type = OSMO_AUTH_TYPE_GSM > + }; Why is that static? > > + memcpy(auth.u.gsm.ki, ainfo.a3a8_ki, sizeof(auth.u.gsm.ki)); > + > + if (osmo_auth_gen_vec(vec, &auth, atuple->rand) < 0) > + return -1; > + > + memcpy(atuple->sres, vec->sres, 4); > + memcpy(atuple->kc, vec->kc, 8); in terms of API, how hard would be an in-situ operation? From Max.Suraev at fairwaves.co Tue Jul 22 12:48:10 2014 From: Max.Suraev at fairwaves.co (=?UTF-8?B?4piO?=) Date: Tue, 22 Jul 2014 14:48:10 +0200 Subject: [PATCH] use osmocom auth API instead of direct calls In-Reply-To: <20140722100103.GA14416@xiaoyu.lan> References: <1401898914-23556-1-git-send-email-Max.Suraev@fairwaves.co> <20140722100103.GA14416@xiaoyu.lan> Message-ID: <53CE5D8A.7060508@fairwaves.co> Curiously I do not see this patch in patchwork anymore. Comments are inline. 22.07.2014 12:01, Holger Hans Peter Freyther ?????: > On Wed, Jun 04, 2014 at 06:21:54PM +0200, Max Suraev wrote: > > Hi! > > sorry for the late reply (and I also intend to reply for reviving > our wednesday meetings. I could talk about TCAP/MAP..) > Neat. >> @@ -76,6 +41,11 @@ int auth_get_tuple_for_subscr(struct gsm_auth_tuple *atuple, >> { >> struct gsm_auth_info ainfo; >> int i, rc; >> + static struct osmo_sub_auth_data auth = { >> + .type = OSMO_AUTH_TYPE_GSM >> + }; > > Why is that static? > Probably crawled from static functions I've replaced :) It's not really needed here. >> >> + memcpy(auth.u.gsm.ki, ainfo.a3a8_ki, sizeof(auth.u.gsm.ki)); >> + >> + if (osmo_auth_gen_vec(vec, &auth, atuple->rand) < 0) >> + return -1; >> + >> + memcpy(atuple->sres, vec->sres, 4); >> + memcpy(atuple->kc, vec->kc, 8); > > in terms of API, how hard would be an in-situ operation? > Ideally we should use osmocom's auth_vec directly instead of our own atuple. But this change would be more intrusive and I recall Sylvain been working on something like that so I've decided to go for smaller patch which does the job of using proper API. -- best regards, Max, http://fairwaves.co From dwillmann at sysmocom.de Wed Jul 2 15:58:14 2014 From: dwillmann at sysmocom.de (Daniel Willmann) Date: Wed, 2 Jul 2014 17:58:14 +0200 Subject: [osmo-pcu 1/3] bts, tbf: Separate functions for dl/ul tbf_by_tlli lookup Message-ID: In the future we want to separate ul and dl tbf into different classes that inherit from a common base. Ticket: SYS#389 Sponsored-by: On-Waves ehf --- src/bts.cpp | 24 +++++++++++++++++------- src/bts.h | 4 +++- src/tbf.cpp | 18 +++++++++--------- tests/tbf/TbfTest.cpp | 12 ++++++------ 4 files changed, 35 insertions(+), 23 deletions(-) diff --git a/src/bts.cpp b/src/bts.cpp index 3dd5705..51be2d9 100644 --- a/src/bts.cpp +++ b/src/bts.cpp @@ -216,6 +216,18 @@ int BTS::add_paging(uint8_t chan_needed, uint8_t *identity_lv) return 0; } +/* search for active downlink tbf */ +gprs_rlcmac_tbf *BTS::dl_tbf_by_tlli(uint32_t tlli) +{ + return tbf_by_tlli(tlli, GPRS_RLCMAC_DL_TBF); +} + +/* search for active uplink tbf */ +gprs_rlcmac_tbf *BTS::ul_tbf_by_tlli(uint32_t tlli) +{ + return tbf_by_tlli(tlli, GPRS_RLCMAC_UL_TBF); +} + /* search for active downlink or uplink tbf */ gprs_rlcmac_tbf *BTS::tbf_by_tlli(uint32_t tlli, enum gprs_rlcmac_tbf_direction dir) { @@ -360,7 +372,7 @@ int BTS::rcv_imm_ass_cnf(const uint8_t *data, uint32_t fn) tlli |= (*data++) << 4; tlli |= (*data++) >> 4; - tbf = tbf_by_tlli(tlli, GPRS_RLCMAC_DL_TBF); + tbf = dl_tbf_by_tlli(tlli); if (!tbf) { LOGP(DRLCMAC, LOGL_ERROR, "Got IMM.ASS confirm, but TLLI=%08x " "does not exit\n", tlli); @@ -725,8 +737,7 @@ void gprs_rlcmac_pdch::rcv_control_ack(Packet_Control_Acknowledgement_t *packet, tbf->n3105 = 0; tbf->dl_ass_state = GPRS_RLCMAC_DL_ASS_NONE; if (tbf->direction == GPRS_RLCMAC_UL_TBF) - tbf = bts()->tbf_by_tlli(tbf->tlli(), - GPRS_RLCMAC_DL_TBF); + tbf = bts()->dl_tbf_by_tlli(tbf->tlli()); #warning "TBF is changing on the way... *sigh*" if (!tbf) { LOGP(DRLCMAC, LOGL_ERROR, "Got ACK, but DL " @@ -753,8 +764,7 @@ void gprs_rlcmac_pdch::rcv_control_ack(Packet_Control_Acknowledgement_t *packet, tbf->ul_ass_state = GPRS_RLCMAC_UL_ASS_NONE; #warning "TBF is changing on the way... *sigh*" if (tbf->direction == GPRS_RLCMAC_DL_TBF) - tbf = bts()->tbf_by_tlli(tbf->tlli(), - GPRS_RLCMAC_UL_TBF); + tbf = bts()->ul_tbf_by_tlli(tbf->tlli()); if (!tbf) { LOGP(DRLCMAC, LOGL_ERROR, "Got ACK, but UL " "TBF is gone TLLI=0x%08x\n", tlli); @@ -836,7 +846,7 @@ void gprs_rlcmac_pdch::rcv_resource_request(Packet_Resource_Request_t *request, struct gprs_rlcmac_tbf *dl_tbf; uint8_t ta; - tbf = bts()->tbf_by_tlli(tlli, GPRS_RLCMAC_UL_TBF); + tbf = bts()->ul_tbf_by_tlli(tlli); if (tbf) { LOGP(DRLCMACUL, LOGL_NOTICE, "Got RACH from " "TLLI=0x%08x while %s still " @@ -846,7 +856,7 @@ void gprs_rlcmac_pdch::rcv_resource_request(Packet_Resource_Request_t *request, tbf = NULL; } - if ((dl_tbf = bts()->tbf_by_tlli(tlli, GPRS_RLCMAC_DL_TBF))) { + if ((dl_tbf = bts()->dl_tbf_by_tlli(tlli))) { LOGP(DRLCMACUL, LOGL_NOTICE, "Got RACH from " "TLLI=0x%08x while %s still exists. " "Killing pending DL TBF\n", tlli, diff --git a/src/bts.h b/src/bts.h index aa68ed7..c83bb18 100644 --- a/src/bts.h +++ b/src/bts.h @@ -192,7 +192,8 @@ public: /** add paging to paging queue(s) */ int add_paging(uint8_t chan_needed, uint8_t *identity_lv); - gprs_rlcmac_tbf *tbf_by_tlli(uint32_t tlli, enum gprs_rlcmac_tbf_direction dir); + gprs_rlcmac_tbf *dl_tbf_by_tlli(uint32_t tlli); + gprs_rlcmac_tbf *ul_tbf_by_tlli(uint32_t tlli); gprs_rlcmac_tbf *tbf_by_poll_fn(uint32_t fn, uint8_t trx, uint8_t ts); gprs_rlcmac_tbf *tbf_by_tfi(uint8_t tfi, uint8_t trx, enum gprs_rlcmac_tbf_direction dir); @@ -238,6 +239,7 @@ private: SBAController m_sba; TimingAdvance m_ta; struct rate_ctr_group *m_ratectrs; + gprs_rlcmac_tbf *tbf_by_tlli(uint32_t tlli, enum gprs_rlcmac_tbf_direction dir); private: /* disable copying to avoid slicing */ diff --git a/src/tbf.cpp b/src/tbf.cpp index 5943674..f913f97 100644 --- a/src/tbf.cpp +++ b/src/tbf.cpp @@ -82,7 +82,7 @@ static struct gprs_rlcmac_tbf *tbf_lookup_dl(BTS *bts, const uint32_t tlli, const char *imsi) { /* TODO: look up by IMSI first, then tlli, then old_tlli */ - return bts->tbf_by_tlli(tlli, GPRS_RLCMAC_DL_TBF); + return bts->dl_tbf_by_tlli(tlli); } int gprs_rlcmac_tbf::append_data(const uint8_t ms_class, @@ -130,7 +130,7 @@ static int tbf_new_dl_assignment(struct gprs_rlcmac_bts *bts, /* check for uplink data, so we copy our informations */ #warning "Do the same look up for IMSI, TLLI and OLD_TLLI" #warning "Refactor the below lines... into a new method" - tbf = bts->bts->tbf_by_tlli(tlli, GPRS_RLCMAC_UL_TBF); + tbf = bts->bts->ul_tbf_by_tlli(tlli); if (tbf && tbf->dir.ul.contention_resolution_done && !tbf->dir.ul.final_ack_sent) { use_trx = tbf->trx->trx_no; @@ -308,7 +308,7 @@ int gprs_rlcmac_tbf::update() if (direction != GPRS_RLCMAC_DL_TBF) return -EINVAL; - ul_tbf = bts->tbf_by_tlli(m_tlli, GPRS_RLCMAC_UL_TBF); + ul_tbf = bts->ul_tbf_by_tlli(m_tlli); tbf_unlink_pdch(this); rc = bts_data->alloc_algorithm(bts_data, ul_tbf, this, bts_data->alloc_algorithm_curst, 0); @@ -1182,7 +1182,7 @@ struct msgb *gprs_rlcmac_tbf::create_dl_ass(uint32_t fn) return NULL; } #warning "THIS should probably go over the IMSI too" - new_tbf = bts->tbf_by_tlli(m_tlli, GPRS_RLCMAC_DL_TBF); + new_tbf = bts->dl_tbf_by_tlli(m_tlli); } else new_tbf = this; if (!new_tbf) { @@ -1252,7 +1252,7 @@ struct msgb *gprs_rlcmac_tbf::create_ul_ass(uint32_t fn) /* on down TBF we get the uplink TBF to be assigned. */ #warning "Probably want to find by IMSI too" if (direction == GPRS_RLCMAC_DL_TBF) - new_tbf = bts->tbf_by_tlli(m_tlli, GPRS_RLCMAC_UL_TBF); + new_tbf = bts->ul_tbf_by_tlli(m_tlli); else new_tbf = this; @@ -1497,7 +1497,7 @@ void gprs_rlcmac_tbf::update_tlli(uint32_t tlli) */ if (m_tlli_valid && direction == GPRS_RLCMAC_DL_TBF) { gprs_rlcmac_tbf *ul_tbf; - ul_tbf = bts->tbf_by_tlli(m_tlli, GPRS_RLCMAC_UL_TBF); + ul_tbf = bts->ul_tbf_by_tlli(m_tlli); if (ul_tbf) { ul_tbf->m_tlli = tlli; @@ -1537,7 +1537,7 @@ int gprs_rlcmac_tbf::extract_tlli(const uint8_t *data, const size_t len) update_tlli(new_tlli); LOGP(DRLCMACUL, LOGL_INFO, "Decoded premier TLLI=0x%08x of " "UL DATA TFI=%d.\n", tlli(), rh->tfi); - if ((dl_tbf = bts->tbf_by_tlli(tlli(), GPRS_RLCMAC_DL_TBF))) { + if ((dl_tbf = bts->dl_tbf_by_tlli(tlli()))) { LOGP(DRLCMACUL, LOGL_NOTICE, "Got RACH from " "TLLI=0x%08x while %s still exists. " "Killing pending DL TBF\n", tlli(), @@ -1545,9 +1545,9 @@ int gprs_rlcmac_tbf::extract_tlli(const uint8_t *data, const size_t len) tbf_free(dl_tbf); dl_tbf = NULL; } - /* tbf_by_tlli will not find your TLLI, because it is not + /* ul_tbf_by_tlli will not find your TLLI, because it is not * yet marked valid */ - if ((ul_tbf = bts->tbf_by_tlli(tlli(), GPRS_RLCMAC_UL_TBF))) { + if ((ul_tbf = bts->ul_tbf_by_tlli(tlli()))) { LOGP(DRLCMACUL, LOGL_NOTICE, "Got RACH from " "TLLI=0x%08x while %s still exists. " "Killing pending UL TBF\n", tlli(), diff --git a/tests/tbf/TbfTest.cpp b/tests/tbf/TbfTest.cpp index 86c5bbd..38975f9 100644 --- a/tests/tbf/TbfTest.cpp +++ b/tests/tbf/TbfTest.cpp @@ -59,8 +59,8 @@ static void test_tbf_tlli_update() ul_tbf->tlli_mark_valid(); - OSMO_ASSERT(the_bts.tbf_by_tlli(0x2342, GPRS_RLCMAC_DL_TBF) == dl_tbf); - OSMO_ASSERT(the_bts.tbf_by_tlli(0x2342, GPRS_RLCMAC_UL_TBF) == ul_tbf); + OSMO_ASSERT(the_bts.dl_tbf_by_tlli(0x2342) == dl_tbf); + OSMO_ASSERT(the_bts.ul_tbf_by_tlli(0x2342) == ul_tbf); /* @@ -68,12 +68,12 @@ static void test_tbf_tlli_update() * has changed. */ dl_tbf->update_tlli(0x4232); - OSMO_ASSERT(!the_bts.tbf_by_tlli(0x2342, GPRS_RLCMAC_DL_TBF)); - OSMO_ASSERT(!the_bts.tbf_by_tlli(0x2342, GPRS_RLCMAC_UL_TBF)); + OSMO_ASSERT(!the_bts.dl_tbf_by_tlli(0x2342)); + OSMO_ASSERT(!the_bts.ul_tbf_by_tlli(0x2342)); - OSMO_ASSERT(the_bts.tbf_by_tlli(0x4232, GPRS_RLCMAC_DL_TBF) == dl_tbf); - OSMO_ASSERT(the_bts.tbf_by_tlli(0x4232, GPRS_RLCMAC_UL_TBF) == ul_tbf); + OSMO_ASSERT(the_bts.dl_tbf_by_tlli(0x4232) == dl_tbf); + OSMO_ASSERT(the_bts.ul_tbf_by_tlli(0x4232) == ul_tbf); OSMO_ASSERT(the_bts.timing_advance()->recall(0x4232) == 4); } -- 1.8.4.2 From dwillmann at sysmocom.de Wed Jul 2 15:58:15 2014 From: dwillmann at sysmocom.de (Daniel Willmann) Date: Wed, 2 Jul 2014 17:58:15 +0200 Subject: [osmo-pcu 2/3] bts: Separate functions for dl/ul tbf_by_tfi lookup In-Reply-To: References: Message-ID: Ticket: SYS#389 Sponsored-by: On-Waves ehf --- src/bts.cpp | 18 +++++++++++++++--- src/bts.h | 4 +++- 2 files changed, 18 insertions(+), 4 deletions(-) diff --git a/src/bts.cpp b/src/bts.cpp index 51be2d9..52960cf 100644 --- a/src/bts.cpp +++ b/src/bts.cpp @@ -271,6 +271,18 @@ gprs_rlcmac_tbf *BTS::tbf_by_poll_fn(uint32_t fn, uint8_t trx, uint8_t ts) return NULL; } +/* lookup downlink TBF Entity (by TFI) */ +gprs_rlcmac_tbf *BTS::dl_tbf_by_tfi(uint8_t tfi, uint8_t trx) +{ + return tbf_by_tfi(tfi, trx, GPRS_RLCMAC_DL_TBF); +} + +/* lookup uplink TBF Entity (by TFI) */ +gprs_rlcmac_tbf *BTS::ul_tbf_by_tfi(uint8_t tfi, uint8_t trx) +{ + return tbf_by_tfi(tfi, trx, GPRS_RLCMAC_UL_TBF); +} + /* lookup TBF Entity (by TFI) */ gprs_rlcmac_tbf *BTS::tbf_by_tfi(uint8_t tfi, uint8_t trx, enum gprs_rlcmac_tbf_direction dir) @@ -690,7 +702,7 @@ int gprs_rlcmac_pdch::rcv_data_block_acknowledged(uint8_t *data, uint8_t len, in } /* find TBF inst from given TFI */ - tbf = bts()->tbf_by_tfi(rh->tfi, trx_no(), GPRS_RLCMAC_UL_TBF); + tbf = bts()->ul_tbf_by_tfi(rh->tfi, trx_no()); if (!tbf) { LOGP(DRLCMACUL, LOGL_NOTICE, "UL DATA unknown TFI=%d\n", rh->tfi); @@ -900,14 +912,14 @@ void gprs_rlcmac_pdch::rcv_resource_request(Packet_Resource_Request_t *request, if (request->ID.u.Global_TFI.UnionType) { int8_t tfi = request->ID.u.Global_TFI.u.DOWNLINK_TFI; - tbf = bts()->tbf_by_tfi(tfi, trx_no(), GPRS_RLCMAC_DL_TBF); + tbf = bts()->dl_tbf_by_tfi(tfi, trx_no()); if (!tbf) { LOGP(DRLCMAC, LOGL_NOTICE, "PACKET RESSOURCE REQ unknown downlink TFI=%d\n", tfi); return; } } else { int8_t tfi = request->ID.u.Global_TFI.u.UPLINK_TFI; - tbf = bts()->tbf_by_tfi(tfi, trx_no(), GPRS_RLCMAC_UL_TBF); + tbf = bts()->ul_tbf_by_tfi(tfi, trx_no()); if (!tbf) { LOGP(DRLCMAC, LOGL_NOTICE, "PACKET RESSOURCE REQ unknown uplink TFI=%d\n", tfi); return; diff --git a/src/bts.h b/src/bts.h index c83bb18..a67f215 100644 --- a/src/bts.h +++ b/src/bts.h @@ -195,7 +195,8 @@ public: gprs_rlcmac_tbf *dl_tbf_by_tlli(uint32_t tlli); gprs_rlcmac_tbf *ul_tbf_by_tlli(uint32_t tlli); gprs_rlcmac_tbf *tbf_by_poll_fn(uint32_t fn, uint8_t trx, uint8_t ts); - gprs_rlcmac_tbf *tbf_by_tfi(uint8_t tfi, uint8_t trx, enum gprs_rlcmac_tbf_direction dir); + gprs_rlcmac_tbf *dl_tbf_by_tfi(uint8_t tfi, uint8_t trx); + gprs_rlcmac_tbf *ul_tbf_by_tfi(uint8_t tfi, uint8_t trx); int tfi_find_free(enum gprs_rlcmac_tbf_direction dir, uint8_t *_trx, int8_t use_trx); @@ -240,6 +241,7 @@ private: TimingAdvance m_ta; struct rate_ctr_group *m_ratectrs; gprs_rlcmac_tbf *tbf_by_tlli(uint32_t tlli, enum gprs_rlcmac_tbf_direction dir); + gprs_rlcmac_tbf *tbf_by_tfi(uint8_t tfi, uint8_t trx, enum gprs_rlcmac_tbf_direction dir); private: /* disable copying to avoid slicing */ -- 1.8.4.2 From dwillmann at sysmocom.de Wed Jul 2 15:58:16 2014 From: dwillmann at sysmocom.de (Daniel Willmann) Date: Wed, 2 Jul 2014 17:58:16 +0200 Subject: [osmo-pcu 3/3] bts: Split tbf_by_poll_fn into separate dl and ul functions In-Reply-To: References: Message-ID: rcv_control_dl_ack_nack is only meaningful for dl tbf while rcv_control_ack can be sent in response to a dl or ul tbf. So rcv_control_ack still needs to check for ul and dl tbfs. Ticket: SYS#389 Sponsored-by: On-Waves ehf --- src/bts.cpp | 21 ++++++++++++++++----- src/bts.h | 3 ++- 2 files changed, 18 insertions(+), 6 deletions(-) diff --git a/src/bts.cpp b/src/bts.cpp index 52960cf..08baee0 100644 --- a/src/bts.cpp +++ b/src/bts.cpp @@ -248,20 +248,28 @@ gprs_rlcmac_tbf *BTS::tbf_by_tlli(uint32_t tlli, enum gprs_rlcmac_tbf_direction return NULL; } -gprs_rlcmac_tbf *BTS::tbf_by_poll_fn(uint32_t fn, uint8_t trx, uint8_t ts) +gprs_rlcmac_tbf *BTS::dl_tbf_by_poll_fn(uint32_t fn, uint8_t trx, uint8_t ts) { struct gprs_rlcmac_tbf *tbf; /* only one TBF can poll on specific TS/FN, because scheduler can only * schedule one downlink control block (with polling) at a FN per TS */ - llist_for_each_entry(tbf, &m_bts.ul_tbfs, list) { + llist_for_each_entry(tbf, &m_bts.dl_tbfs, list) { if (tbf->state_is_not(GPRS_RLCMAC_RELEASING) && tbf->poll_state == GPRS_RLCMAC_POLL_SCHED && tbf->poll_fn == fn && tbf->trx->trx_no == trx && tbf->control_ts == ts) return tbf; } - llist_for_each_entry(tbf, &m_bts.dl_tbfs, list) { + return NULL; +} +gprs_rlcmac_tbf *BTS::ul_tbf_by_poll_fn(uint32_t fn, uint8_t trx, uint8_t ts) +{ + struct gprs_rlcmac_tbf *tbf; + + /* only one TBF can poll on specific TS/FN, because scheduler can only + * schedule one downlink control block (with polling) at a FN per TS */ + llist_for_each_entry(tbf, &m_bts.ul_tbfs, list) { if (tbf->state_is_not(GPRS_RLCMAC_RELEASING) && tbf->poll_state == GPRS_RLCMAC_POLL_SCHED && tbf->poll_fn == fn && tbf->trx->trx_no == trx @@ -718,7 +726,10 @@ void gprs_rlcmac_pdch::rcv_control_ack(Packet_Control_Acknowledgement_t *packet, uint32_t tlli = 0; tlli = packet->TLLI; - tbf = bts()->tbf_by_poll_fn(fn, trx_no(), ts_no); + tbf = bts()->ul_tbf_by_poll_fn(fn, trx_no(), ts_no); + if (!tbf) + tbf = bts()->dl_tbf_by_poll_fn(fn, trx_no(), ts_no); + if (!tbf) { LOGP(DRLCMAC, LOGL_NOTICE, "PACKET CONTROL ACK with " "unknown FN=%u TLLI=0x%08x (TRX %d TS %d)\n", @@ -804,7 +815,7 @@ void gprs_rlcmac_pdch::rcv_control_dl_ack_nack(Packet_Downlink_Ack_Nack_t *ack_n int rc; tfi = ack_nack->DOWNLINK_TFI; - tbf = bts()->tbf_by_poll_fn(fn, trx_no(), ts_no); + tbf = bts()->dl_tbf_by_poll_fn(fn, trx_no(), ts_no); if (!tbf) { LOGP(DRLCMAC, LOGL_NOTICE, "PACKET DOWNLINK ACK with " "unknown FN=%u TFI=%d (TRX %d TS %d)\n", diff --git a/src/bts.h b/src/bts.h index a67f215..621bcba 100644 --- a/src/bts.h +++ b/src/bts.h @@ -194,7 +194,8 @@ public: gprs_rlcmac_tbf *dl_tbf_by_tlli(uint32_t tlli); gprs_rlcmac_tbf *ul_tbf_by_tlli(uint32_t tlli); - gprs_rlcmac_tbf *tbf_by_poll_fn(uint32_t fn, uint8_t trx, uint8_t ts); + gprs_rlcmac_tbf *dl_tbf_by_poll_fn(uint32_t fn, uint8_t trx, uint8_t ts); + gprs_rlcmac_tbf *ul_tbf_by_poll_fn(uint32_t fn, uint8_t trx, uint8_t ts); gprs_rlcmac_tbf *dl_tbf_by_tfi(uint8_t tfi, uint8_t trx); gprs_rlcmac_tbf *ul_tbf_by_tfi(uint8_t tfi, uint8_t trx); -- 1.8.4.2 From jerlbeck at sysmocom.de Thu Jul 3 11:28:12 2014 From: jerlbeck at sysmocom.de (Jacob Erlbeck) Date: Thu, 3 Jul 2014 13:28:12 +0200 Subject: [PATCH 1/6] gprs/test: Add additional gbproxy tests Message-ID: <1404386897-27883-1-git-send-email-jerlbeck@sysmocom.de> This adds a test case with several messages to test BSSGP patching. New messages: - BSSGP/DTAP Attach Request - BSSGP/DTAP Attach Accept - BSSGP/DTAP Routing Area Update Request - BSSGP/DTAP Routing Area Update Accept - BSSGP/DTAP Activate PDP Context Request - BSSGP SUSPEND - BSSGP SUSPEND ACK Sponsored-by: On-Waves ehf --- openbsc/tests/gbproxy/gbproxy_test.c | 199 ++++++++++++++++++++++++- openbsc/tests/gbproxy/gbproxy_test.ok | 268 ++++++++++++++++++++++++++++++++++ 2 files changed, 466 insertions(+), 1 deletion(-) diff --git a/openbsc/tests/gbproxy/gbproxy_test.c b/openbsc/tests/gbproxy/gbproxy_test.c index ea07a77..c372af1 100644 --- a/openbsc/tests/gbproxy/gbproxy_test.c +++ b/openbsc/tests/gbproxy/gbproxy_test.c @@ -28,13 +28,88 @@ #include #include +#include #define REMOTE_BSS_ADDR 0x01020304 #define REMOTE_SGSN_ADDR 0x05060708 #define SGSN_NSEI 0x0100 -struct gbproxy_config gbcfg; +struct gbproxy_config gbcfg = {0}; + +/* Base Station Subsystem GPRS Protocol: GSM A-I/F DTAP - Attach Request */ +static const unsigned char bssgp_attach_req[75] = { + 0x01, 0xbb, 0xc5, 0x46, 0x79, 0x00, 0x00, 0x04, + 0x08, 0x88, 0x11, 0x22, 0x33, 0x40, 0x50, 0x60, + 0x75, 0x30, 0x00, 0x80, 0x0e, 0x00, 0x34, 0x01, + 0xc0, 0x01, 0x08, 0x01, 0x02, 0xf5, 0xe0, 0x21, + 0x08, 0x02, 0x05, 0xf4, 0xfb, 0xc5, 0x46, 0x79, + 0x11, 0x22, 0x33, 0x40, 0x50, 0x60, 0x19, 0x18, + 0xb3, 0x43, 0x2b, 0x25, 0x96, 0x62, 0x00, 0x60, + 0x80, 0x9a, 0xc2, 0xc6, 0x62, 0x00, 0x60, 0x80, + 0xba, 0xc8, 0xc6, 0x62, 0x00, 0x60, 0x80, 0x00, + 0x16, 0x6d, 0x01 +}; + +/* Base Station Subsystem GPRS Protocol: GSM A-I/F DTAP - Attach Accept */ +static const unsigned char bssgp_attach_acc[88] = { + 0x00, 0xbb, 0xc5, 0x46, 0x79, 0x00, 0x50, 0x20, + 0x16, 0x82, 0x02, 0x58, 0x13, 0x99, 0x18, 0xb3, + 0x43, 0x2b, 0x25, 0x96, 0x62, 0x00, 0x60, 0x80, + 0x9a, 0xc2, 0xc6, 0x62, 0x00, 0x60, 0x80, 0xba, + 0xc8, 0xc6, 0x62, 0x00, 0x60, 0x80, 0x00, 0x0a, + 0x82, 0x08, 0x02, 0x0d, 0x88, 0x11, 0x12, 0x13, + 0x14, 0x15, 0x16, 0x17, 0x18, 0x00, 0x81, 0x00, + 0x0e, 0x9e, 0x41, 0xc0, 0x05, 0x08, 0x02, 0x01, + 0x49, 0x04, 0x21, 0x63, 0x54, 0x40, 0x50, 0x60, + 0x19, 0xcd, 0xd7, 0x08, 0x17, 0x16, 0x18, 0x05, + 0xf4, 0xfb, 0xc5, 0x47, 0x22, 0x42, 0x67, 0x9a +}; + +/* Base Station Subsystem GPRS Protocol: GSM A-I/F DTAP - Routing Area Update Request */ +static const unsigned char bssgp_ra_upd_req[85] = { + 0x01, 0xaf, 0xe2, 0x80, 0x6e, 0x00, 0x00, 0x04, + 0x08, 0x88, 0x11, 0x22, 0x33, 0x40, 0x50, 0x60, + 0x70, 0x80, 0x00, 0x80, 0x0e, 0x00, 0x3e, 0x01, + 0xc0, 0x15, 0x08, 0x08, 0x10, 0x11, 0x22, 0x33, + 0x40, 0x50, 0x60, 0x1d, 0x19, 0x13, 0x42, 0x33, + 0x57, 0x2b, 0xf7, 0xc8, 0x48, 0x02, 0x13, 0x48, + 0x50, 0xc8, 0x48, 0x02, 0x14, 0x48, 0x50, 0xc8, + 0x48, 0x02, 0x17, 0x49, 0x10, 0xc8, 0x48, 0x02, + 0x00, 0x19, 0x8b, 0xb2, 0x92, 0x17, 0x16, 0x27, + 0x07, 0x04, 0x31, 0x02, 0xe5, 0xe0, 0x32, 0x02, + 0x20, 0x00, 0x96, 0x3e, 0x97 +}; + +/* Base Station Subsystem GPRS Protocol: GSM A-I/F DTAP - Routing Area Update Accept */ +static const unsigned char bssgp_ra_upd_acc[91] = { + 0x00, 0xaf, 0xe2, 0x80, 0x6e, 0x00, 0x50, 0x20, + 0x16, 0x82, 0x02, 0x58, 0x13, 0x9d, 0x19, 0x13, + 0x42, 0x33, 0x57, 0x2b, 0xf7, 0xc8, 0x48, 0x02, + 0x13, 0x48, 0x50, 0xc8, 0x48, 0x02, 0x14, 0x48, + 0x50, 0xc8, 0x48, 0x02, 0x17, 0x49, 0x10, 0xc8, + 0x48, 0x02, 0x00, 0x0a, 0x82, 0x07, 0x04, 0x0d, + 0x88, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, + 0x18, 0x00, 0x81, 0x00, 0x0e, 0x9d, 0x41, 0xc0, + 0x19, 0x08, 0x09, 0x00, 0x49, 0x21, 0x63, 0x54, + 0x40, 0x50, 0x60, 0x19, 0x54, 0xab, 0xb3, 0x18, + 0x05, 0xf4, 0xef, 0xe2, 0x81, 0x17, 0x17, 0x16, + 0xc3, 0xbf, 0xcc +}; + +/* Base Station Subsystem GPRS Protocol: GSM A-I/F DTAP - Activate PDP Context Request */ +static const unsigned char bssgp_act_pdp_ctx_req[76] = { + 0x01, 0xef, 0xe2, 0xb7, 0x00, 0x00, 0x00, 0x04, + 0x08, 0x88, 0x11, 0x22, 0x33, 0x40, 0x50, 0x60, + 0x75, 0x30, 0x00, 0x80, 0x0e, 0x00, 0x35, 0x01, + 0xc0, 0x0d, 0x0a, 0x41, 0x05, 0x03, 0x0c, 0x00, + 0x00, 0x1f, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x02, 0x01, 0x21, 0x28, 0x03, + 0x02, 0x61, 0x62, 0x27, 0x14, 0x80, 0x80, 0x21, + 0x10, 0x01, 0x00, 0x00, 0x10, 0x81, 0x06, 0x00, + 0x00, 0x00, 0x00, 0x83, 0x06, 0x00, 0x00, 0x00, + 0x00, 0x5a, 0xff, 0x02 +}; static int gprs_process_message(struct gprs_ns_inst *nsi, const char *text, struct sockaddr_in *peer, const unsigned char* data, @@ -168,6 +243,39 @@ static void send_bssgp_reset_ack(struct gprs_ns_inst *nsi, send_ns_unitdata(nsi, "BVC_RESET_ACK", src_addr, 0, msg, sizeof(msg)); } +static void send_bssgp_suspend(struct gprs_ns_inst *nsi, + struct sockaddr_in *src_addr, + struct gprs_ra_id *raid) +{ + /* Base Station Subsystem GPRS Protocol, BSSGP SUSPEND */ + unsigned char msg[15] = { + 0x0b, 0x1f, 0x84, 0xcc, 0xd1, 0x75, 0x8b, 0x1b, + 0x86, 0x11, 0x22, 0x33, 0x40, 0x50, 0x60 + }; + + if (raid) + gsm48_construct_ra(msg + 9, raid); + + send_ns_unitdata(nsi, "BVC_SUSPEND", src_addr, 0, msg, sizeof(msg)); +} + +static void send_bssgp_suspend_ack(struct gprs_ns_inst *nsi, + struct sockaddr_in *src_addr, + struct gprs_ra_id *raid) +{ + /* Base Station Subsystem GPRS Protocol, BSSGP SUSPEND ACK */ + unsigned char msg[18] = { + 0x0c, 0x1f, 0x84, 0xcc, 0xd1, 0x75, 0x8b, 0x1b, + 0x86, 0x11, 0x22, 0x33, 0x40, 0x50, 0x60, 0x1d, + 0x81, 0x01 + }; + + if (raid) + gsm48_construct_ra(msg + 9, raid); + + send_ns_unitdata(nsi, "BVC_SUSPEND_ACK", src_addr, 0, msg, sizeof(msg)); +} + static void setup_ns(struct gprs_ns_inst *nsi, struct sockaddr_in *src_addr, uint16_t nsvci, uint16_t nsei) { @@ -686,6 +794,94 @@ static void test_gbproxy_ident_changes() gbprox_reset(); } +static void test_gbproxy_ra_patching() +{ + struct gprs_ns_inst *nsi = gprs_ns_instantiate(gprs_ns_callback, NULL); + struct sockaddr_in bss_peer[1] = {{0},}; + struct sockaddr_in sgsn_peer= {0}; + struct gprs_ra_id rai_bss = + {.mcc = 112, .mnc = 332, .lac = 16464, .rac = 96}; + struct gprs_ra_id rai_sgsn = + {.mcc = 123, .mnc = 456, .lac = 16464, .rac = 96}; + struct gprs_ra_id rai_unknown = + {.mcc = 1, .mnc = 99, .lac = 99, .rac = 96}; + + bssgp_nsi = nsi; + gbcfg.nsi = bssgp_nsi; + gbcfg.nsip_sgsn_nsei = SGSN_NSEI; + + sgsn_peer.sin_family = AF_INET; + sgsn_peer.sin_port = htons(32000); + sgsn_peer.sin_addr.s_addr = htonl(REMOTE_SGSN_ADDR); + + bss_peer[0].sin_family = AF_INET; + bss_peer[0].sin_port = htons(1111); + bss_peer[0].sin_addr.s_addr = htonl(REMOTE_BSS_ADDR); + + printf("--- Initialise SGSN ---\n\n"); + + gprs_ns_nsip_connect(nsi, &sgsn_peer, SGSN_NSEI, SGSN_NSEI+1); + send_ns_reset_ack(nsi, &sgsn_peer, SGSN_NSEI+1, SGSN_NSEI); + send_ns_alive_ack(nsi, &sgsn_peer); + send_ns_unblock_ack(nsi, &sgsn_peer); + send_ns_alive(nsi, &sgsn_peer); + gprs_dump_nsi(nsi); + + printf("--- Initialise BSS 1 ---\n\n"); + + setup_ns(nsi, &bss_peer[0], 0x1001, 0x1000); + setup_bssgp(nsi, &bss_peer[0], 0x1002); + gprs_dump_nsi(nsi); + gbprox_dump_peers(stdout, 0, 1); + + send_bssgp_reset_ack(nsi, &sgsn_peer, 0x1002); + + send_bssgp_suspend(nsi, &bss_peer[0], &rai_bss); + send_bssgp_suspend_ack(nsi, &sgsn_peer, &rai_sgsn); + + gbprox_dump_global(stdout, 0, 1); + gbprox_dump_peers(stdout, 0, 1); + + printf("--- Send message from BSS 1 to SGSN, BVCI 0x1002 ---\n\n"); + + send_ns_unitdata(nsi, NULL, &bss_peer[0], 0x1002, + bssgp_attach_req, sizeof(bssgp_attach_req)); + + send_ns_unitdata(nsi, NULL, &sgsn_peer, 0x1002, + bssgp_attach_acc, sizeof(bssgp_attach_acc)); + + send_ns_unitdata(nsi, NULL, &bss_peer[0], 0x1002, + bssgp_ra_upd_req, sizeof(bssgp_ra_upd_req)); + + send_ns_unitdata(nsi, NULL, &sgsn_peer, 0x1002, + bssgp_ra_upd_acc, sizeof(bssgp_ra_upd_acc)); + + /* Replace APN */ + send_ns_unitdata(nsi, NULL, &bss_peer[0], 0x1002, + bssgp_act_pdp_ctx_req, sizeof(bssgp_act_pdp_ctx_req)); + + /* TODO: Re-configure to test APN IE removal */ + + /* Remove APN */ + send_ns_unitdata(nsi, NULL, &bss_peer[0], 0x1002, + bssgp_act_pdp_ctx_req, sizeof(bssgp_act_pdp_ctx_req)); + + gbprox_dump_global(stdout, 0, 1); + gbprox_dump_peers(stdout, 0, 1); + + printf("--- Bad cases ---\n\n"); + + send_bssgp_reset_ack(nsi, &sgsn_peer, 0x1eee); + send_bssgp_suspend_ack(nsi, &sgsn_peer, &rai_unknown); + + gbprox_dump_global(stdout, 0, 1); + gbprox_dump_peers(stdout, 0, 1); + + gprs_ns_destroy(nsi); + nsi = NULL; + gbprox_reset(); +} + static struct log_info info = {}; @@ -706,6 +902,7 @@ int main(int argc, char **argv) printf("===== GbProxy test START\n"); test_gbproxy(); test_gbproxy_ident_changes(); + test_gbproxy_ra_patching(); printf("===== GbProxy test END\n\n"); exit(EXIT_SUCCESS); diff --git a/openbsc/tests/gbproxy/gbproxy_test.ok b/openbsc/tests/gbproxy/gbproxy_test.ok index 3b25922..58add97 100644 --- a/openbsc/tests/gbproxy/gbproxy_test.ok +++ b/openbsc/tests/gbproxy/gbproxy_test.ok @@ -1518,5 +1518,273 @@ Peers: NS Transmission error : 2 NSEI 8192, BVCI 4098, not blocked, RAI 112-332-16464-96 NSEI mismatch : 1 +--- Initialise SGSN --- + +MESSAGE to SGSN at 0x05060708:32000, msg length 12 +02 00 81 01 01 82 01 01 04 82 01 00 + +PROCESSING RESET_ACK from 0x05060708:32000 +03 01 82 01 01 04 82 01 00 + +MESSAGE to SGSN at 0x05060708:32000, msg length 1 +0a + +result (RESET_ACK) = 1 + +PROCESSING ALIVE_ACK from 0x05060708:32000 +0b + +MESSAGE to SGSN at 0x05060708:32000, msg length 1 +06 + +result (ALIVE_ACK) = 1 + +PROCESSING UNBLOCK_ACK from 0x05060708:32000 +07 + +==> got signal NS_UNBLOCK, NS-VC 0x0101/5.6.7.8:32000 + +result (UNBLOCK_ACK) = 0 + +PROCESSING ALIVE from 0x05060708:32000 +0a + +MESSAGE to SGSN at 0x05060708:32000, msg length 1 +0b + +result (ALIVE) = 1 + +Current NS-VCIs: + VCI 0x0101, NSEI 0x0100, peer 0x05060708:32000 + NS-VC Block count : 1 + +--- Initialise BSS 1 --- + +Setup NS-VC: remote 0x01020304:1111, NSVCI 0x1001(4097), NSEI 0x1000(4096) + +PROCESSING RESET from 0x01020304:1111 +02 00 81 01 01 82 10 01 04 82 10 00 + +==> got signal NS_RESET, NS-VC 0x1001/1.2.3.4:1111 + +MESSAGE to BSS at 0x01020304:1111, msg length 9 +03 01 82 10 01 04 82 10 00 + +MESSAGE to BSS at 0x01020304:1111, msg length 1 +0a + +result (RESET) = 9 + +PROCESSING ALIVE from 0x01020304:1111 +0a + +MESSAGE to BSS at 0x01020304:1111, msg length 1 +0b + +result (ALIVE) = 1 + +PROCESSING UNBLOCK from 0x01020304:1111 +06 + +==> got signal NS_UNBLOCK, NS-VC 0x1001/1.2.3.4:1111 + +MESSAGE to BSS at 0x01020304:1111, msg length 1 +07 + +result (UNBLOCK) = 1 + +PROCESSING ALIVE_ACK from 0x01020304:1111 +0b + +result (ALIVE_ACK) = 0 + +Setup BSSGP: remote 0x01020304:1111, BVCI 0x1002(4098) + +PROCESSING BVC_RESET from 0x01020304:1111 +00 00 00 00 22 04 82 10 02 07 81 08 08 88 11 22 33 40 50 60 10 00 00 00 00 00 + +CALLBACK, event 0, msg length 22, bvci 0x0000 +22 04 82 10 02 07 81 08 08 88 11 22 33 40 50 60 10 00 00 00 00 00 + +NS UNITDATA MESSAGE to SGSN, BVCI 0x0000, msg length 22 +22 04 82 10 02 07 81 08 08 88 11 22 33 40 50 60 10 00 00 00 00 00 + +MESSAGE to SGSN at 0x05060708:32000, msg length 26 +00 00 00 00 22 04 82 10 02 07 81 08 08 88 11 22 33 40 50 60 10 00 00 00 00 00 + +result (BVC_RESET) = 26 + +Current NS-VCIs: + VCI 0x1001, NSEI 0x1000, peer 0x01020304:1111 + VCI 0x0101, NSEI 0x0100, peer 0x05060708:32000 + NS-VC Block count : 1 + +Peers: + NSEI 4096, BVCI 4098, not blocked, RAI 112-332-16464-96 +PROCESSING BVC_RESET_ACK from 0x05060708:32000 +00 00 00 00 23 04 82 10 02 + +CALLBACK, event 0, msg length 5, bvci 0x0000 +23 04 82 10 02 + +NS UNITDATA MESSAGE to BSS, BVCI 0x0000, msg length 5 +23 04 82 10 02 + +MESSAGE to BSS at 0x01020304:1111, msg length 9 +00 00 00 00 23 04 82 10 02 + +result (BVC_RESET_ACK) = 9 + +PROCESSING BVC_SUSPEND from 0x01020304:1111 +00 00 00 00 0b 1f 84 cc d1 75 8b 1b 86 11 22 33 40 50 60 + +CALLBACK, event 0, msg length 15, bvci 0x0000 +0b 1f 84 cc d1 75 8b 1b 86 11 22 33 40 50 60 + +NS UNITDATA MESSAGE to SGSN, BVCI 0x0000, msg length 15 +0b 1f 84 cc d1 75 8b 1b 86 11 22 33 40 50 60 + +MESSAGE to SGSN at 0x05060708:32000, msg length 19 +00 00 00 00 0b 1f 84 cc d1 75 8b 1b 86 11 22 33 40 50 60 + +result (BVC_SUSPEND) = 19 + +PROCESSING BVC_SUSPEND_ACK from 0x05060708:32000 +00 00 00 00 0c 1f 84 cc d1 75 8b 1b 86 21 63 54 40 50 60 1d 81 01 + +CALLBACK, event 0, msg length 18, bvci 0x0000 +0c 1f 84 cc d1 75 8b 1b 86 21 63 54 40 50 60 1d 81 01 + +NS UNITDATA MESSAGE to SGSN, BVCI 0x0000, msg length 24 +41 07 81 05 15 92 0c 1f 84 cc d1 75 8b 1b 86 21 63 54 40 50 60 1d 81 01 + +MESSAGE to SGSN at 0x05060708:32000, msg length 28 +00 00 00 00 41 07 81 05 15 92 0c 1f 84 cc d1 75 8b 1b 86 21 63 54 40 50 60 1d 81 01 + +result (BVC_SUSPEND_ACK) = 28 + +Gbproxy global: + Invalid Routing Area Identifier : 1 +Peers: + NSEI 4096, BVCI 4098, not blocked, RAI 112-332-16464-96 +--- Send message from BSS 1 to SGSN, BVCI 0x1002 --- + +PROCESSING UNITDATA from 0x01020304:1111 +00 00 10 02 01 bb c5 46 79 00 00 04 08 88 11 22 33 40 50 60 75 30 00 80 0e 00 34 01 c0 01 08 01 02 f5 e0 21 08 02 05 f4 fb c5 46 79 11 22 33 40 50 60 19 18 b3 43 2b 25 96 62 00 60 80 9a c2 c6 62 00 60 80 ba c8 c6 62 00 60 80 00 16 6d 01 + +CALLBACK, event 0, msg length 75, bvci 0x1002 +01 bb c5 46 79 00 00 04 08 88 11 22 33 40 50 60 75 30 00 80 0e 00 34 01 c0 01 08 01 02 f5 e0 21 08 02 05 f4 fb c5 46 79 11 22 33 40 50 60 19 18 b3 43 2b 25 96 62 00 60 80 9a c2 c6 62 00 60 80 ba c8 c6 62 00 60 80 00 16 6d 01 + +NS UNITDATA MESSAGE to SGSN, BVCI 0x1002, msg length 75 +01 bb c5 46 79 00 00 04 08 88 11 22 33 40 50 60 75 30 00 80 0e 00 34 01 c0 01 08 01 02 f5 e0 21 08 02 05 f4 fb c5 46 79 11 22 33 40 50 60 19 18 b3 43 2b 25 96 62 00 60 80 9a c2 c6 62 00 60 80 ba c8 c6 62 00 60 80 00 16 6d 01 + +MESSAGE to SGSN at 0x05060708:32000, msg length 79 +00 00 10 02 01 bb c5 46 79 00 00 04 08 88 11 22 33 40 50 60 75 30 00 80 0e 00 34 01 c0 01 08 01 02 f5 e0 21 08 02 05 f4 fb c5 46 79 11 22 33 40 50 60 19 18 b3 43 2b 25 96 62 00 60 80 9a c2 c6 62 00 60 80 ba c8 c6 62 00 60 80 00 16 6d 01 + +result (UNITDATA) = 79 + +PROCESSING UNITDATA from 0x05060708:32000 +00 00 10 02 00 bb c5 46 79 00 50 20 16 82 02 58 13 99 18 b3 43 2b 25 96 62 00 60 80 9a c2 c6 62 00 60 80 ba c8 c6 62 00 60 80 00 0a 82 08 02 0d 88 11 12 13 14 15 16 17 18 00 81 00 0e 9e 41 c0 05 08 02 01 49 04 21 63 54 40 50 60 19 cd d7 08 17 16 18 05 f4 fb c5 47 22 42 67 9a + +CALLBACK, event 0, msg length 88, bvci 0x1002 +00 bb c5 46 79 00 50 20 16 82 02 58 13 99 18 b3 43 2b 25 96 62 00 60 80 9a c2 c6 62 00 60 80 ba c8 c6 62 00 60 80 00 0a 82 08 02 0d 88 11 12 13 14 15 16 17 18 00 81 00 0e 9e 41 c0 05 08 02 01 49 04 21 63 54 40 50 60 19 cd d7 08 17 16 18 05 f4 fb c5 47 22 42 67 9a + +NS UNITDATA MESSAGE to BSS, BVCI 0x1002, msg length 88 +00 bb c5 46 79 00 50 20 16 82 02 58 13 99 18 b3 43 2b 25 96 62 00 60 80 9a c2 c6 62 00 60 80 ba c8 c6 62 00 60 80 00 0a 82 08 02 0d 88 11 12 13 14 15 16 17 18 00 81 00 0e 9e 41 c0 05 08 02 01 49 04 21 63 54 40 50 60 19 cd d7 08 17 16 18 05 f4 fb c5 47 22 42 67 9a + +MESSAGE to BSS at 0x01020304:1111, msg length 92 +00 00 10 02 00 bb c5 46 79 00 50 20 16 82 02 58 13 99 18 b3 43 2b 25 96 62 00 60 80 9a c2 c6 62 00 60 80 ba c8 c6 62 00 60 80 00 0a 82 08 02 0d 88 11 12 13 14 15 16 17 18 00 81 00 0e 9e 41 c0 05 08 02 01 49 04 21 63 54 40 50 60 19 cd d7 08 17 16 18 05 f4 fb c5 47 22 42 67 9a + +result (UNITDATA) = 92 + +PROCESSING UNITDATA from 0x01020304:1111 +00 00 10 02 01 af e2 80 6e 00 00 04 08 88 11 22 33 40 50 60 70 80 00 80 0e 00 3e 01 c0 15 08 08 10 11 22 33 40 50 60 1d 19 13 42 33 57 2b f7 c8 48 02 13 48 50 c8 48 02 14 48 50 c8 48 02 17 49 10 c8 48 02 00 19 8b b2 92 17 16 27 07 04 31 02 e5 e0 32 02 20 00 96 3e 97 + +CALLBACK, event 0, msg length 85, bvci 0x1002 +01 af e2 80 6e 00 00 04 08 88 11 22 33 40 50 60 70 80 00 80 0e 00 3e 01 c0 15 08 08 10 11 22 33 40 50 60 1d 19 13 42 33 57 2b f7 c8 48 02 13 48 50 c8 48 02 14 48 50 c8 48 02 17 49 10 c8 48 02 00 19 8b b2 92 17 16 27 07 04 31 02 e5 e0 32 02 20 00 96 3e 97 + +NS UNITDATA MESSAGE to SGSN, BVCI 0x1002, msg length 85 +01 af e2 80 6e 00 00 04 08 88 11 22 33 40 50 60 70 80 00 80 0e 00 3e 01 c0 15 08 08 10 11 22 33 40 50 60 1d 19 13 42 33 57 2b f7 c8 48 02 13 48 50 c8 48 02 14 48 50 c8 48 02 17 49 10 c8 48 02 00 19 8b b2 92 17 16 27 07 04 31 02 e5 e0 32 02 20 00 96 3e 97 + +MESSAGE to SGSN at 0x05060708:32000, msg length 89 +00 00 10 02 01 af e2 80 6e 00 00 04 08 88 11 22 33 40 50 60 70 80 00 80 0e 00 3e 01 c0 15 08 08 10 11 22 33 40 50 60 1d 19 13 42 33 57 2b f7 c8 48 02 13 48 50 c8 48 02 14 48 50 c8 48 02 17 49 10 c8 48 02 00 19 8b b2 92 17 16 27 07 04 31 02 e5 e0 32 02 20 00 96 3e 97 + +result (UNITDATA) = 89 + +PROCESSING UNITDATA from 0x05060708:32000 +00 00 10 02 00 af e2 80 6e 00 50 20 16 82 02 58 13 9d 19 13 42 33 57 2b f7 c8 48 02 13 48 50 c8 48 02 14 48 50 c8 48 02 17 49 10 c8 48 02 00 0a 82 07 04 0d 88 11 12 13 14 15 16 17 18 00 81 00 0e 9d 41 c0 19 08 09 00 49 21 63 54 40 50 60 19 54 ab b3 18 05 f4 ef e2 81 17 17 16 c3 bf cc + +CALLBACK, event 0, msg length 91, bvci 0x1002 +00 af e2 80 6e 00 50 20 16 82 02 58 13 9d 19 13 42 33 57 2b f7 c8 48 02 13 48 50 c8 48 02 14 48 50 c8 48 02 17 49 10 c8 48 02 00 0a 82 07 04 0d 88 11 12 13 14 15 16 17 18 00 81 00 0e 9d 41 c0 19 08 09 00 49 21 63 54 40 50 60 19 54 ab b3 18 05 f4 ef e2 81 17 17 16 c3 bf cc + +NS UNITDATA MESSAGE to BSS, BVCI 0x1002, msg length 91 +00 af e2 80 6e 00 50 20 16 82 02 58 13 9d 19 13 42 33 57 2b f7 c8 48 02 13 48 50 c8 48 02 14 48 50 c8 48 02 17 49 10 c8 48 02 00 0a 82 07 04 0d 88 11 12 13 14 15 16 17 18 00 81 00 0e 9d 41 c0 19 08 09 00 49 21 63 54 40 50 60 19 54 ab b3 18 05 f4 ef e2 81 17 17 16 c3 bf cc + +MESSAGE to BSS at 0x01020304:1111, msg length 95 +00 00 10 02 00 af e2 80 6e 00 50 20 16 82 02 58 13 9d 19 13 42 33 57 2b f7 c8 48 02 13 48 50 c8 48 02 14 48 50 c8 48 02 17 49 10 c8 48 02 00 0a 82 07 04 0d 88 11 12 13 14 15 16 17 18 00 81 00 0e 9d 41 c0 19 08 09 00 49 21 63 54 40 50 60 19 54 ab b3 18 05 f4 ef e2 81 17 17 16 c3 bf cc + +result (UNITDATA) = 95 + +PROCESSING UNITDATA from 0x01020304:1111 +00 00 10 02 01 ef e2 b7 00 00 00 04 08 88 11 22 33 40 50 60 75 30 00 80 0e 00 35 01 c0 0d 0a 41 05 03 0c 00 00 1f 10 00 00 00 00 00 00 00 00 02 01 21 28 03 02 61 62 27 14 80 80 21 10 01 00 00 10 81 06 00 00 00 00 83 06 00 00 00 00 5a ff 02 + +CALLBACK, event 0, msg length 76, bvci 0x1002 +01 ef e2 b7 00 00 00 04 08 88 11 22 33 40 50 60 75 30 00 80 0e 00 35 01 c0 0d 0a 41 05 03 0c 00 00 1f 10 00 00 00 00 00 00 00 00 02 01 21 28 03 02 61 62 27 14 80 80 21 10 01 00 00 10 81 06 00 00 00 00 83 06 00 00 00 00 5a ff 02 + +NS UNITDATA MESSAGE to SGSN, BVCI 0x1002, msg length 76 +01 ef e2 b7 00 00 00 04 08 88 11 22 33 40 50 60 75 30 00 80 0e 00 35 01 c0 0d 0a 41 05 03 0c 00 00 1f 10 00 00 00 00 00 00 00 00 02 01 21 28 03 02 61 62 27 14 80 80 21 10 01 00 00 10 81 06 00 00 00 00 83 06 00 00 00 00 5a ff 02 + +MESSAGE to SGSN at 0x05060708:32000, msg length 80 +00 00 10 02 01 ef e2 b7 00 00 00 04 08 88 11 22 33 40 50 60 75 30 00 80 0e 00 35 01 c0 0d 0a 41 05 03 0c 00 00 1f 10 00 00 00 00 00 00 00 00 02 01 21 28 03 02 61 62 27 14 80 80 21 10 01 00 00 10 81 06 00 00 00 00 83 06 00 00 00 00 5a ff 02 + +result (UNITDATA) = 80 + +PROCESSING UNITDATA from 0x01020304:1111 +00 00 10 02 01 ef e2 b7 00 00 00 04 08 88 11 22 33 40 50 60 75 30 00 80 0e 00 35 01 c0 0d 0a 41 05 03 0c 00 00 1f 10 00 00 00 00 00 00 00 00 02 01 21 28 03 02 61 62 27 14 80 80 21 10 01 00 00 10 81 06 00 00 00 00 83 06 00 00 00 00 5a ff 02 + +CALLBACK, event 0, msg length 76, bvci 0x1002 +01 ef e2 b7 00 00 00 04 08 88 11 22 33 40 50 60 75 30 00 80 0e 00 35 01 c0 0d 0a 41 05 03 0c 00 00 1f 10 00 00 00 00 00 00 00 00 02 01 21 28 03 02 61 62 27 14 80 80 21 10 01 00 00 10 81 06 00 00 00 00 83 06 00 00 00 00 5a ff 02 + +NS UNITDATA MESSAGE to SGSN, BVCI 0x1002, msg length 76 +01 ef e2 b7 00 00 00 04 08 88 11 22 33 40 50 60 75 30 00 80 0e 00 35 01 c0 0d 0a 41 05 03 0c 00 00 1f 10 00 00 00 00 00 00 00 00 02 01 21 28 03 02 61 62 27 14 80 80 21 10 01 00 00 10 81 06 00 00 00 00 83 06 00 00 00 00 5a ff 02 + +MESSAGE to SGSN at 0x05060708:32000, msg length 80 +00 00 10 02 01 ef e2 b7 00 00 00 04 08 88 11 22 33 40 50 60 75 30 00 80 0e 00 35 01 c0 0d 0a 41 05 03 0c 00 00 1f 10 00 00 00 00 00 00 00 00 02 01 21 28 03 02 61 62 27 14 80 80 21 10 01 00 00 10 81 06 00 00 00 00 83 06 00 00 00 00 5a ff 02 + +result (UNITDATA) = 80 + +Gbproxy global: + Invalid Routing Area Identifier : 1 +Peers: + NSEI 4096, BVCI 4098, not blocked, RAI 112-332-16464-96 +--- Bad cases --- + +PROCESSING BVC_RESET_ACK from 0x05060708:32000 +00 00 00 00 23 04 82 1e ee + +CALLBACK, event 0, msg length 5, bvci 0x0000 +23 04 82 1e ee + +result (BVC_RESET_ACK) = -2 + +PROCESSING BVC_SUSPEND_ACK from 0x05060708:32000 +00 00 00 00 0c 1f 84 cc d1 75 8b 1b 86 00 f1 99 00 63 60 1d 81 01 + +CALLBACK, event 0, msg length 18, bvci 0x0000 +0c 1f 84 cc d1 75 8b 1b 86 00 f1 99 00 63 60 1d 81 01 + +NS UNITDATA MESSAGE to SGSN, BVCI 0x0000, msg length 24 +41 07 81 05 15 92 0c 1f 84 cc d1 75 8b 1b 86 00 f1 99 00 63 60 1d 81 01 + +MESSAGE to SGSN at 0x05060708:32000, msg length 28 +00 00 00 00 41 07 81 05 15 92 0c 1f 84 cc d1 75 8b 1b 86 00 f1 99 00 63 60 1d 81 01 + +result (BVC_SUSPEND_ACK) = 28 + +Gbproxy global: + Invalid BVC Identifier : 1 + Invalid Routing Area Identifier : 2 +Peers: + NSEI 4096, BVCI 4098, not blocked, RAI 112-332-16464-96 ===== GbProxy test END -- 1.9.1 From jerlbeck at sysmocom.de Thu Jul 3 11:28:13 2014 From: jerlbeck at sysmocom.de (Jacob Erlbeck) Date: Thu, 3 Jul 2014 13:28:13 +0200 Subject: [PATCH 2/6] gprs/test: Increase stderr log level In-Reply-To: <1404386897-27883-1-git-send-email-jerlbeck@sysmocom.de> References: <1404386897-27883-1-git-send-email-jerlbeck@sysmocom.de> Message-ID: <1404386897-27883-2-git-send-email-jerlbeck@sysmocom.de> Enable the generation of more log messages. Sponsored-by: On-Waves ehf --- openbsc/tests/gbproxy/gbproxy_test.c | 26 ++++++++++++++++++++++++-- 1 file changed, 24 insertions(+), 2 deletions(-) diff --git a/openbsc/tests/gbproxy/gbproxy_test.c b/openbsc/tests/gbproxy/gbproxy_test.c index c372af1..2aaf109 100644 --- a/openbsc/tests/gbproxy/gbproxy_test.c +++ b/openbsc/tests/gbproxy/gbproxy_test.c @@ -883,7 +883,28 @@ static void test_gbproxy_ra_patching() } -static struct log_info info = {}; +static struct log_info_cat gprs_categories[] = { + [DGPRS] = { + .name = "DGPRS", + .description = "GPRS Packet Service", + .enabled = 1, .loglevel = LOGL_DEBUG, + }, + [DNS] = { + .name = "DNS", + .description = "GPRS Network Service (NS)", + .enabled = 1, .loglevel = LOGL_INFO, + }, + [DBSSGP] = { + .name = "DBSSGP", + .description = "GPRS BSS Gateway Protocol (BSSGP)", + .enabled = 1, .loglevel = LOGL_DEBUG, + }, +}; + +static struct log_info info = { + .cat = gprs_categories, + .num_cat = ARRAY_SIZE(gprs_categories), +}; int main(int argc, char **argv) { @@ -893,7 +914,8 @@ int main(int argc, char **argv) osmo_signal_register_handler(SS_L_NS, &test_signal, NULL); log_set_print_filename(osmo_stderr_target, 0); - log_set_log_level(osmo_stderr_target, LOGL_INFO); + log_set_log_level(osmo_stderr_target, LOGL_DEBUG); + log_set_all_filter(osmo_stderr_target, 1); rate_ctr_init(NULL); -- 1.9.1 From jerlbeck at sysmocom.de Thu Jul 3 11:28:14 2014 From: jerlbeck at sysmocom.de (Jacob Erlbeck) Date: Thu, 3 Jul 2014 13:28:14 +0200 Subject: [PATCH 3/6] gprs: Implement BSSGP MCC/MNC patching In-Reply-To: <1404386897-27883-1-git-send-email-jerlbeck@sysmocom.de> References: <1404386897-27883-1-git-send-email-jerlbeck@sysmocom.de> Message-ID: <1404386897-27883-3-git-send-email-jerlbeck@sysmocom.de> This adds a feature to patch the BSSGP MNC/MCC fields of messages going to and coming from the SGSN. To enable this feature, the gbproxy's VTY commands 'core-mobile-country-code' and/or 'core-mobile-network-code' must be used. All packets to the SGSN are patched to match the configured values. Packets received from the SGSN are patched to the corresponding values as last seen from the BSS side. Note that this will probably not work with a gbproxy used for several BSS simultaneously. Note also, that MCC/MNC contained in a LLC IE will not be patched. Ticket: OW#1185 Sponsored-by: On-Waves ehf --- openbsc/include/openbsc/gb_proxy.h | 4 + openbsc/src/gprs/Makefile.am | 3 +- openbsc/src/gprs/gb_proxy.c | 133 ++++++++++++++++++++++++++++++++++ openbsc/src/gprs/gb_proxy_main.c | 2 +- openbsc/src/gprs/gb_proxy_vty.c | 52 +++++++++++++ openbsc/tests/gbproxy/Makefile.am | 2 + openbsc/tests/gbproxy/gbproxy_test.c | 2 + openbsc/tests/gbproxy/gbproxy_test.ok | 48 ++++++------ 8 files changed, 222 insertions(+), 24 deletions(-) diff --git a/openbsc/include/openbsc/gb_proxy.h b/openbsc/include/openbsc/gb_proxy.h index 4d189a6..220636e 100644 --- a/openbsc/include/openbsc/gb_proxy.h +++ b/openbsc/include/openbsc/gb_proxy.h @@ -13,6 +13,10 @@ struct gbproxy_config { /* misc */ struct gprs_ns_inst *nsi; + + /* force mcc/mnc */ + int core_mnc; + int core_mcc; }; extern struct gbproxy_config gbcfg; diff --git a/openbsc/src/gprs/Makefile.am b/openbsc/src/gprs/Makefile.am index 049d41d..87dbc30 100644 --- a/openbsc/src/gprs/Makefile.am +++ b/openbsc/src/gprs/Makefile.am @@ -13,7 +13,8 @@ else bin_PROGRAMS = osmo-gbproxy endif -osmo_gbproxy_SOURCES = gb_proxy.c gb_proxy_main.c gb_proxy_vty.c +osmo_gbproxy_SOURCES = gb_proxy.c gb_proxy_main.c gb_proxy_vty.c \ + gprs_llc_parse.c crc24.c osmo_gbproxy_LDADD = $(top_builddir)/src/libcommon/libcommon.a \ $(OSMO_LIBS) diff --git a/openbsc/src/gprs/gb_proxy.c b/openbsc/src/gprs/gb_proxy.c index 4799344..61059bb 100644 --- a/openbsc/src/gprs/gb_proxy.c +++ b/openbsc/src/gprs/gb_proxy.c @@ -43,6 +43,10 @@ #include #include +#include +#include +#include + enum gbprox_global_ctr { GBPROX_GLOB_CTR_INV_BVCI, GBPROX_GLOB_CTR_INV_LAI, @@ -55,6 +59,9 @@ enum gbprox_global_ctr { GBPROX_GLOB_CTR_RESTART_RESET_SGSN, GBPROX_GLOB_CTR_TX_ERR_SGSN, GBPROX_GLOB_CTR_OTHER_ERR, + GBPROX_GLOB_CTR_RAID_PATCHED_BSS, + GBPROX_GLOB_CTR_RAID_PATCHED_SGSN, + GBPROX_GLOB_CTR_PATCH_ERR, }; static const struct rate_ctr_desc global_ctr_description[] = { @@ -69,6 +76,9 @@ static const struct rate_ctr_desc global_ctr_description[] = { { "restart.sgsn", "Restarted RESET procedure (SGSN)" }, { "tx-err.sgsn", "NS Transmission error (SGSN)" }, { "error", "Other error " }, + { "raid-mod.bss", "RAID patched (BSS )" }, + { "raid-mod.sgsn", "RAID patched (SGSN)" }, + { "mod-err", "Patching error " }, }; static const struct rate_ctr_group_desc global_ctrg_desc = { @@ -112,6 +122,11 @@ static const struct rate_ctr_group_desc peer_ctrg_desc = { .ctr_desc = peer_ctr_description, }; +static struct gbprox_patch_state { + int local_mnc; + int local_mcc; +} gbprox_patch_state = {0}; + struct gbprox_peer { struct llist_head list; @@ -260,6 +275,119 @@ static void strip_ns_hdr(struct msgb *msg) msgb_pull(msg, strip_len); } +/* patch RA identifier in place, update peer accordingly */ +static void gbprox_patch_raid(uint8_t *raid_enc, struct gbprox_patch_state *state, + int to_bss, const char *log_text) +{ + int old_local_mcc = state->local_mcc; + int old_local_mnc = state->local_mnc; + int old_mcc; + int old_mnc; + struct gprs_ra_id raid; + + gsm48_parse_ra(&raid, raid_enc); + + old_mcc = raid.mcc; + old_mnc = raid.mnc; + + if (!to_bss) { + /* BSS -> SGSN */ + /* save BSS side MCC/MNC */ + if (!gbcfg.core_mcc || raid.mcc == gbcfg.core_mcc) { + state->local_mcc = 0; + } else { + state->local_mcc = raid.mcc; + raid.mcc = gbcfg.core_mcc; + } + + if (!gbcfg.core_mnc || raid.mnc == gbcfg.core_mnc) { + state->local_mnc = 0; + } else { + state->local_mnc = raid.mnc; + raid.mnc = gbcfg.core_mnc; + } + } else { + /* SGSN -> BSS */ + if (state->local_mcc) + raid.mcc = state->local_mcc; + + if (state->local_mnc) + raid.mnc = state->local_mnc; + } + + if (old_local_mcc != state->local_mcc || + old_local_mnc != state->local_mnc) + LOGP(DGPRS, LOGL_NOTICE, + "Patching RAID %sactivated, msg: %s, " + "local: %d-%d, core: %d-%d, to %s\n", + state->local_mcc || state->local_mnc ? + "" : "de", + log_text, + state->local_mcc, state->local_mnc, + gbcfg.core_mcc, gbcfg.core_mnc, + to_bss ? "BSS" : "SGSN"); + + if (state->local_mcc || state->local_mnc) { + enum gbprox_global_ctr counter = + to_bss ? + GBPROX_GLOB_CTR_RAID_PATCHED_SGSN : + GBPROX_GLOB_CTR_RAID_PATCHED_BSS; + + LOGP(DGPRS, LOGL_DEBUG, + "Patching %s to %s: " + "%d-%d-%d-%d -> %d-%d-%d-%d\n", + log_text, + to_bss ? "BSS" : "SGSN", + old_mcc, old_mnc, raid.lac, raid.rac, + raid.mcc, raid.mnc, raid.lac, raid.rac); + + gsm48_construct_ra(raid_enc, &raid); + rate_ctr_inc(&get_global_ctrg()->ctr[counter]); + } +} + +/* patch BSSGP message to use core_mcc/mnc on the SGSN side */ +static void gbprox_patch_bssgp_message(struct msgb *msg, int to_bss) +{ + struct bssgp_normal_hdr *bgph; + struct bssgp_ud_hdr *budh; + struct tlv_parsed tp; + uint8_t pdu_type; + struct gbprox_patch_state *state = &gbprox_patch_state; + uint8_t *data; + size_t data_len; + + if (!gbcfg.core_mcc && !gbcfg.core_mnc) + return; + + bgph = (struct bssgp_normal_hdr *) msgb_bssgph(msg); + budh = (struct bssgp_ud_hdr *) msgb_bssgph(msg); + pdu_type = bgph->pdu_type; + + if (to_bss && !state->local_mcc && !state->local_mnc) + return; + + if (pdu_type == BSSGP_PDUT_UL_UNITDATA || + pdu_type == BSSGP_PDUT_DL_UNITDATA) { + data = budh->data; + data_len = msgb_bssgp_len(msg) - sizeof(*budh); + } else { + data = bgph->data; + data_len = msgb_bssgp_len(msg) - sizeof(*bgph); + } + + /* fix BSSGP */ + bssgp_tlv_parse(&tp, data, data_len); + + if (TLVP_PRESENT(&tp, BSSGP_IE_ROUTEING_AREA)) + gbprox_patch_raid((uint8_t *)TLVP_VAL(&tp, BSSGP_IE_ROUTEING_AREA), + state, to_bss, "ROUTING_AREA"); + + if (TLVP_PRESENT(&tp, BSSGP_IE_CELL_ID)) + gbprox_patch_raid((uint8_t *)TLVP_VAL(&tp, BSSGP_IE_CELL_ID), + state, to_bss, "CELL_ID"); +} + /* feed a message down the NS-VC associated with the specified peer */ static int gbprox_relay2sgsn(struct msgb *old_msg, uint16_t ns_bvci) { @@ -276,6 +404,8 @@ static int gbprox_relay2sgsn(struct msgb *old_msg, uint16_t ns_bvci) strip_ns_hdr(msg); + gbprox_patch_bssgp_message(msg, 0); + rc = gprs_ns_sendmsg(bssgp_nsi, msg); if (rc < 0) rate_ctr_inc(&get_global_ctrg()->ctr[GBPROX_GLOB_CTR_TX_ERR_SGSN]); @@ -679,6 +809,9 @@ int gbprox_rcvmsg(struct msgb *msg, uint16_t nsei, uint16_t ns_bvci, uint16_t ns struct gbprox_peer *peer; int remote_end_is_sgsn = nsei == gbcfg.nsip_sgsn_nsei; + if (remote_end_is_sgsn) + gbprox_patch_bssgp_message(msg, 1); + /* Only BVCI=0 messages need special treatment */ if (ns_bvci == 0 || ns_bvci == 1) { if (remote_end_is_sgsn) diff --git a/openbsc/src/gprs/gb_proxy_main.c b/openbsc/src/gprs/gb_proxy_main.c index ff2e14b..1f140d4 100644 --- a/openbsc/src/gprs/gb_proxy_main.c +++ b/openbsc/src/gprs/gb_proxy_main.c @@ -66,7 +66,7 @@ const char *openbsc_copyright = "There is NO WARRANTY, to the extent permitted by law.\r\n"; static char *config_file = "osmo_gbproxy.cfg"; -struct gbproxy_config gbcfg; +struct gbproxy_config gbcfg = {0}; static int daemonize = 0; /* Pointer to the SGSN peer */ diff --git a/openbsc/src/gprs/gb_proxy_vty.c b/openbsc/src/gprs/gb_proxy_vty.c index 2de0d3b..acd8051 100644 --- a/openbsc/src/gprs/gb_proxy_vty.c +++ b/openbsc/src/gprs/gb_proxy_vty.c @@ -51,6 +51,13 @@ static int config_write_gbproxy(struct vty *vty) vty_out(vty, " sgsn nsei %u%s", g_cfg->nsip_sgsn_nsei, VTY_NEWLINE); + if (g_cfg->core_mcc > 0) + vty_out(vty, " core-mobile-country-code %d%s", + g_cfg->core_mcc, VTY_NEWLINE); + if (g_cfg->core_mnc > 0) + vty_out(vty, " core-mobile-network-code %d%s", + g_cfg->core_mnc, VTY_NEWLINE); + return CMD_SUCCESS; } @@ -76,6 +83,47 @@ DEFUN(cfg_nsip_sgsn_nsei, return CMD_SUCCESS; } +#define GBPROXY_CORE_MNC_STR "Use this network code for the backbone\n" + +DEFUN(cfg_gbproxy_core_mnc, + cfg_gbproxy_core_mnc_cmd, + "core-mobile-network-code <1-999>", + GBPROXY_CORE_MNC_STR "NCC value\n") +{ + g_cfg->core_mnc = atoi(argv[0]); + return CMD_SUCCESS; +} + +DEFUN(cfg_gbproxy_no_core_mnc, + cfg_gbproxy_no_core_mnc_cmd, + "no core-mobile-network-code", + NO_STR GBPROXY_CORE_MNC_STR) +{ + g_cfg->core_mnc = 0; + return CMD_SUCCESS; +} + +#define GBPROXY_CORE_MCC_STR "Use this country code for the backbone\n" + +DEFUN(cfg_gbproxy_core_mcc, + cfg_gbproxy_core_mcc_cmd, + "core-mobile-country-code <1-999>", + GBPROXY_CORE_MCC_STR "MCC value\n") +{ + g_cfg->core_mcc = atoi(argv[0]); + return CMD_SUCCESS; +} + +DEFUN(cfg_gbproxy_no_core_mcc, + cfg_gbproxy_no_core_mcc_cmd, + "no core-mobile-country-code", + NO_STR GBPROXY_CORE_MCC_STR) +{ + g_cfg->core_mcc = 0; + return CMD_SUCCESS; +} + + int gbproxy_vty_init(void) { install_element_ve(&show_gbproxy_cmd); @@ -87,6 +135,10 @@ int gbproxy_vty_init(void) install_node(&gbproxy_node, config_write_gbproxy); vty_install_default(GBPROXY_NODE); install_element(GBPROXY_NODE, &cfg_nsip_sgsn_nsei_cmd); + install_element(GBPROXY_NODE, &cfg_gbproxy_core_mcc_cmd); + install_element(GBPROXY_NODE, &cfg_gbproxy_core_mnc_cmd); + install_element(GBPROXY_NODE, &cfg_gbproxy_no_core_mcc_cmd); + install_element(GBPROXY_NODE, &cfg_gbproxy_no_core_mnc_cmd); return 0; } diff --git a/openbsc/tests/gbproxy/Makefile.am b/openbsc/tests/gbproxy/Makefile.am index 8e88dc4..9c1b2d0 100644 --- a/openbsc/tests/gbproxy/Makefile.am +++ b/openbsc/tests/gbproxy/Makefile.am @@ -9,6 +9,8 @@ noinst_PROGRAMS = gbproxy_test gbproxy_test_SOURCES = gbproxy_test.c gbproxy_test_LDADD = \ $(top_builddir)/src/gprs/gb_proxy.o \ + $(top_builddir)/src/gprs/gprs_llc_parse.o \ + $(top_builddir)/src/gprs/crc24.o \ $(top_builddir)/src/libcommon/libcommon.a \ $(top_builddir)/src/libbsc/libbsc.a \ $(top_builddir)/src/libtrau/libtrau.a \ diff --git a/openbsc/tests/gbproxy/gbproxy_test.c b/openbsc/tests/gbproxy/gbproxy_test.c index 2aaf109..8bf9527 100644 --- a/openbsc/tests/gbproxy/gbproxy_test.c +++ b/openbsc/tests/gbproxy/gbproxy_test.c @@ -809,6 +809,8 @@ static void test_gbproxy_ra_patching() bssgp_nsi = nsi; gbcfg.nsi = bssgp_nsi; gbcfg.nsip_sgsn_nsei = SGSN_NSEI; + gbcfg.core_mcc = 123; + gbcfg.core_mnc = 456; sgsn_peer.sin_family = AF_INET; sgsn_peer.sin_port = htons(32000); diff --git a/openbsc/tests/gbproxy/gbproxy_test.ok b/openbsc/tests/gbproxy/gbproxy_test.ok index 58add97..f8bd1e7 100644 --- a/openbsc/tests/gbproxy/gbproxy_test.ok +++ b/openbsc/tests/gbproxy/gbproxy_test.ok @@ -1607,10 +1607,10 @@ CALLBACK, event 0, msg length 22, bvci 0x0000 22 04 82 10 02 07 81 08 08 88 11 22 33 40 50 60 10 00 00 00 00 00 NS UNITDATA MESSAGE to SGSN, BVCI 0x0000, msg length 22 -22 04 82 10 02 07 81 08 08 88 11 22 33 40 50 60 10 00 00 00 00 00 +22 04 82 10 02 07 81 08 08 88 21 63 54 40 50 60 10 00 00 00 00 00 MESSAGE to SGSN at 0x05060708:32000, msg length 26 -00 00 00 00 22 04 82 10 02 07 81 08 08 88 11 22 33 40 50 60 10 00 00 00 00 00 +00 00 00 00 22 04 82 10 02 07 81 08 08 88 21 63 54 40 50 60 10 00 00 00 00 00 result (BVC_RESET) = 26 @@ -1642,10 +1642,10 @@ CALLBACK, event 0, msg length 15, bvci 0x0000 0b 1f 84 cc d1 75 8b 1b 86 11 22 33 40 50 60 NS UNITDATA MESSAGE to SGSN, BVCI 0x0000, msg length 15 -0b 1f 84 cc d1 75 8b 1b 86 11 22 33 40 50 60 +0b 1f 84 cc d1 75 8b 1b 86 21 63 54 40 50 60 MESSAGE to SGSN at 0x05060708:32000, msg length 19 -00 00 00 00 0b 1f 84 cc d1 75 8b 1b 86 11 22 33 40 50 60 +00 00 00 00 0b 1f 84 cc d1 75 8b 1b 86 21 63 54 40 50 60 result (BVC_SUSPEND) = 19 @@ -1655,16 +1655,17 @@ PROCESSING BVC_SUSPEND_ACK from 0x05060708:32000 CALLBACK, event 0, msg length 18, bvci 0x0000 0c 1f 84 cc d1 75 8b 1b 86 21 63 54 40 50 60 1d 81 01 -NS UNITDATA MESSAGE to SGSN, BVCI 0x0000, msg length 24 -41 07 81 05 15 92 0c 1f 84 cc d1 75 8b 1b 86 21 63 54 40 50 60 1d 81 01 +NS UNITDATA MESSAGE to BSS, BVCI 0x0000, msg length 18 +0c 1f 84 cc d1 75 8b 1b 86 11 22 33 40 50 60 1d 81 01 -MESSAGE to SGSN at 0x05060708:32000, msg length 28 -00 00 00 00 41 07 81 05 15 92 0c 1f 84 cc d1 75 8b 1b 86 21 63 54 40 50 60 1d 81 01 +MESSAGE to BSS at 0x01020304:1111, msg length 22 +00 00 00 00 0c 1f 84 cc d1 75 8b 1b 86 11 22 33 40 50 60 1d 81 01 -result (BVC_SUSPEND_ACK) = 28 +result (BVC_SUSPEND_ACK) = 22 Gbproxy global: - Invalid Routing Area Identifier : 1 + RAID patched (BSS ): 2 + RAID patched (SGSN): 1 Peers: NSEI 4096, BVCI 4098, not blocked, RAI 112-332-16464-96 --- Send message from BSS 1 to SGSN, BVCI 0x1002 --- @@ -1676,10 +1677,10 @@ CALLBACK, event 0, msg length 75, bvci 0x1002 01 bb c5 46 79 00 00 04 08 88 11 22 33 40 50 60 75 30 00 80 0e 00 34 01 c0 01 08 01 02 f5 e0 21 08 02 05 f4 fb c5 46 79 11 22 33 40 50 60 19 18 b3 43 2b 25 96 62 00 60 80 9a c2 c6 62 00 60 80 ba c8 c6 62 00 60 80 00 16 6d 01 NS UNITDATA MESSAGE to SGSN, BVCI 0x1002, msg length 75 -01 bb c5 46 79 00 00 04 08 88 11 22 33 40 50 60 75 30 00 80 0e 00 34 01 c0 01 08 01 02 f5 e0 21 08 02 05 f4 fb c5 46 79 11 22 33 40 50 60 19 18 b3 43 2b 25 96 62 00 60 80 9a c2 c6 62 00 60 80 ba c8 c6 62 00 60 80 00 16 6d 01 +01 bb c5 46 79 00 00 04 08 88 21 63 54 40 50 60 75 30 00 80 0e 00 34 01 c0 01 08 01 02 f5 e0 21 08 02 05 f4 fb c5 46 79 11 22 33 40 50 60 19 18 b3 43 2b 25 96 62 00 60 80 9a c2 c6 62 00 60 80 ba c8 c6 62 00 60 80 00 16 6d 01 MESSAGE to SGSN at 0x05060708:32000, msg length 79 -00 00 10 02 01 bb c5 46 79 00 00 04 08 88 11 22 33 40 50 60 75 30 00 80 0e 00 34 01 c0 01 08 01 02 f5 e0 21 08 02 05 f4 fb c5 46 79 11 22 33 40 50 60 19 18 b3 43 2b 25 96 62 00 60 80 9a c2 c6 62 00 60 80 ba c8 c6 62 00 60 80 00 16 6d 01 +00 00 10 02 01 bb c5 46 79 00 00 04 08 88 21 63 54 40 50 60 75 30 00 80 0e 00 34 01 c0 01 08 01 02 f5 e0 21 08 02 05 f4 fb c5 46 79 11 22 33 40 50 60 19 18 b3 43 2b 25 96 62 00 60 80 9a c2 c6 62 00 60 80 ba c8 c6 62 00 60 80 00 16 6d 01 result (UNITDATA) = 79 @@ -1704,10 +1705,10 @@ CALLBACK, event 0, msg length 85, bvci 0x1002 01 af e2 80 6e 00 00 04 08 88 11 22 33 40 50 60 70 80 00 80 0e 00 3e 01 c0 15 08 08 10 11 22 33 40 50 60 1d 19 13 42 33 57 2b f7 c8 48 02 13 48 50 c8 48 02 14 48 50 c8 48 02 17 49 10 c8 48 02 00 19 8b b2 92 17 16 27 07 04 31 02 e5 e0 32 02 20 00 96 3e 97 NS UNITDATA MESSAGE to SGSN, BVCI 0x1002, msg length 85 -01 af e2 80 6e 00 00 04 08 88 11 22 33 40 50 60 70 80 00 80 0e 00 3e 01 c0 15 08 08 10 11 22 33 40 50 60 1d 19 13 42 33 57 2b f7 c8 48 02 13 48 50 c8 48 02 14 48 50 c8 48 02 17 49 10 c8 48 02 00 19 8b b2 92 17 16 27 07 04 31 02 e5 e0 32 02 20 00 96 3e 97 +01 af e2 80 6e 00 00 04 08 88 21 63 54 40 50 60 70 80 00 80 0e 00 3e 01 c0 15 08 08 10 11 22 33 40 50 60 1d 19 13 42 33 57 2b f7 c8 48 02 13 48 50 c8 48 02 14 48 50 c8 48 02 17 49 10 c8 48 02 00 19 8b b2 92 17 16 27 07 04 31 02 e5 e0 32 02 20 00 96 3e 97 MESSAGE to SGSN at 0x05060708:32000, msg length 89 -00 00 10 02 01 af e2 80 6e 00 00 04 08 88 11 22 33 40 50 60 70 80 00 80 0e 00 3e 01 c0 15 08 08 10 11 22 33 40 50 60 1d 19 13 42 33 57 2b f7 c8 48 02 13 48 50 c8 48 02 14 48 50 c8 48 02 17 49 10 c8 48 02 00 19 8b b2 92 17 16 27 07 04 31 02 e5 e0 32 02 20 00 96 3e 97 +00 00 10 02 01 af e2 80 6e 00 00 04 08 88 21 63 54 40 50 60 70 80 00 80 0e 00 3e 01 c0 15 08 08 10 11 22 33 40 50 60 1d 19 13 42 33 57 2b f7 c8 48 02 13 48 50 c8 48 02 14 48 50 c8 48 02 17 49 10 c8 48 02 00 19 8b b2 92 17 16 27 07 04 31 02 e5 e0 32 02 20 00 96 3e 97 result (UNITDATA) = 89 @@ -1732,10 +1733,10 @@ CALLBACK, event 0, msg length 76, bvci 0x1002 01 ef e2 b7 00 00 00 04 08 88 11 22 33 40 50 60 75 30 00 80 0e 00 35 01 c0 0d 0a 41 05 03 0c 00 00 1f 10 00 00 00 00 00 00 00 00 02 01 21 28 03 02 61 62 27 14 80 80 21 10 01 00 00 10 81 06 00 00 00 00 83 06 00 00 00 00 5a ff 02 NS UNITDATA MESSAGE to SGSN, BVCI 0x1002, msg length 76 -01 ef e2 b7 00 00 00 04 08 88 11 22 33 40 50 60 75 30 00 80 0e 00 35 01 c0 0d 0a 41 05 03 0c 00 00 1f 10 00 00 00 00 00 00 00 00 02 01 21 28 03 02 61 62 27 14 80 80 21 10 01 00 00 10 81 06 00 00 00 00 83 06 00 00 00 00 5a ff 02 +01 ef e2 b7 00 00 00 04 08 88 21 63 54 40 50 60 75 30 00 80 0e 00 35 01 c0 0d 0a 41 05 03 0c 00 00 1f 10 00 00 00 00 00 00 00 00 02 01 21 28 03 02 61 62 27 14 80 80 21 10 01 00 00 10 81 06 00 00 00 00 83 06 00 00 00 00 5a ff 02 MESSAGE to SGSN at 0x05060708:32000, msg length 80 -00 00 10 02 01 ef e2 b7 00 00 00 04 08 88 11 22 33 40 50 60 75 30 00 80 0e 00 35 01 c0 0d 0a 41 05 03 0c 00 00 1f 10 00 00 00 00 00 00 00 00 02 01 21 28 03 02 61 62 27 14 80 80 21 10 01 00 00 10 81 06 00 00 00 00 83 06 00 00 00 00 5a ff 02 +00 00 10 02 01 ef e2 b7 00 00 00 04 08 88 21 63 54 40 50 60 75 30 00 80 0e 00 35 01 c0 0d 0a 41 05 03 0c 00 00 1f 10 00 00 00 00 00 00 00 00 02 01 21 28 03 02 61 62 27 14 80 80 21 10 01 00 00 10 81 06 00 00 00 00 83 06 00 00 00 00 5a ff 02 result (UNITDATA) = 80 @@ -1746,15 +1747,16 @@ CALLBACK, event 0, msg length 76, bvci 0x1002 01 ef e2 b7 00 00 00 04 08 88 11 22 33 40 50 60 75 30 00 80 0e 00 35 01 c0 0d 0a 41 05 03 0c 00 00 1f 10 00 00 00 00 00 00 00 00 02 01 21 28 03 02 61 62 27 14 80 80 21 10 01 00 00 10 81 06 00 00 00 00 83 06 00 00 00 00 5a ff 02 NS UNITDATA MESSAGE to SGSN, BVCI 0x1002, msg length 76 -01 ef e2 b7 00 00 00 04 08 88 11 22 33 40 50 60 75 30 00 80 0e 00 35 01 c0 0d 0a 41 05 03 0c 00 00 1f 10 00 00 00 00 00 00 00 00 02 01 21 28 03 02 61 62 27 14 80 80 21 10 01 00 00 10 81 06 00 00 00 00 83 06 00 00 00 00 5a ff 02 +01 ef e2 b7 00 00 00 04 08 88 21 63 54 40 50 60 75 30 00 80 0e 00 35 01 c0 0d 0a 41 05 03 0c 00 00 1f 10 00 00 00 00 00 00 00 00 02 01 21 28 03 02 61 62 27 14 80 80 21 10 01 00 00 10 81 06 00 00 00 00 83 06 00 00 00 00 5a ff 02 MESSAGE to SGSN at 0x05060708:32000, msg length 80 -00 00 10 02 01 ef e2 b7 00 00 00 04 08 88 11 22 33 40 50 60 75 30 00 80 0e 00 35 01 c0 0d 0a 41 05 03 0c 00 00 1f 10 00 00 00 00 00 00 00 00 02 01 21 28 03 02 61 62 27 14 80 80 21 10 01 00 00 10 81 06 00 00 00 00 83 06 00 00 00 00 5a ff 02 +00 00 10 02 01 ef e2 b7 00 00 00 04 08 88 21 63 54 40 50 60 75 30 00 80 0e 00 35 01 c0 0d 0a 41 05 03 0c 00 00 1f 10 00 00 00 00 00 00 00 00 02 01 21 28 03 02 61 62 27 14 80 80 21 10 01 00 00 10 81 06 00 00 00 00 83 06 00 00 00 00 5a ff 02 result (UNITDATA) = 80 Gbproxy global: - Invalid Routing Area Identifier : 1 + RAID patched (BSS ): 6 + RAID patched (SGSN): 1 Peers: NSEI 4096, BVCI 4098, not blocked, RAI 112-332-16464-96 --- Bad cases --- @@ -1774,16 +1776,18 @@ CALLBACK, event 0, msg length 18, bvci 0x0000 0c 1f 84 cc d1 75 8b 1b 86 00 f1 99 00 63 60 1d 81 01 NS UNITDATA MESSAGE to SGSN, BVCI 0x0000, msg length 24 -41 07 81 05 15 92 0c 1f 84 cc d1 75 8b 1b 86 00 f1 99 00 63 60 1d 81 01 +41 07 81 05 15 92 0c 1f 84 cc d1 75 8b 1b 86 11 22 33 00 63 60 1d 81 01 MESSAGE to SGSN at 0x05060708:32000, msg length 28 -00 00 00 00 41 07 81 05 15 92 0c 1f 84 cc d1 75 8b 1b 86 00 f1 99 00 63 60 1d 81 01 +00 00 00 00 41 07 81 05 15 92 0c 1f 84 cc d1 75 8b 1b 86 11 22 33 00 63 60 1d 81 01 result (BVC_SUSPEND_ACK) = 28 Gbproxy global: Invalid BVC Identifier : 1 - Invalid Routing Area Identifier : 2 + Invalid Routing Area Identifier : 1 + RAID patched (BSS ): 6 + RAID patched (SGSN): 2 Peers: NSEI 4096, BVCI 4098, not blocked, RAI 112-332-16464-96 ===== GbProxy test END -- 1.9.1 From holger at freyther.de Mon Jul 7 18:19:57 2014 From: holger at freyther.de (Holger Hans Peter Freyther) Date: Mon, 7 Jul 2014 20:19:57 +0200 Subject: [PATCH 3/6] gprs: Implement BSSGP MCC/MNC patching In-Reply-To: <1404386897-27883-3-git-send-email-jerlbeck@sysmocom.de> References: <1404386897-27883-1-git-send-email-jerlbeck@sysmocom.de> <1404386897-27883-3-git-send-email-jerlbeck@sysmocom.de> Message-ID: <20140707181957.GA11978@xiaoyu.lan> On Thu, Jul 03, 2014 at 01:28:14PM +0200, Jacob Erlbeck wrote: Good Evening Jacob, > + int old_local_mcc = state->local_mcc; > + int old_local_mnc = state->local_mnc; make the above two const please. > + if (old_local_mcc != state->local_mcc || > + old_local_mnc != state->local_mnc) > + LOGP(DGPRS, LOGL_NOTICE, > + "Patching RAID %sactivated, msg: %s, " > + "local: %d-%d, core: %d-%d, to %s\n", > + state->local_mcc || state->local_mnc ? > + "" : "de", > + log_text, > + state->local_mcc, state->local_mnc, > + gbcfg.core_mcc, gbcfg.core_mnc, > + to_bss ? "BSS" : "SGSN"); > + > + if (state->local_mcc || state->local_mnc) { What does this extra check/message bring to the table? Why is it a notice? > + /* fix BSSGP */ > + bssgp_tlv_parse(&tp, data, data_len); What exactly is fixed here? > -struct gbproxy_config gbcfg; > +struct gbproxy_config gbcfg = {0}; We were lucky before or did the gbcfg end in the BSS before the patch as well? > +#define GBPROXY_CORE_MNC_STR "Use this network code for the backbone\n" No idea if "core-network" is any better. From jerlbeck at sysmocom.de Thu Jul 3 11:28:15 2014 From: jerlbeck at sysmocom.de (Jacob Erlbeck) Date: Thu, 3 Jul 2014 13:28:15 +0200 Subject: [PATCH 4/6] gprs: Add MCC/MNC patch support for LLC/GMM messages In-Reply-To: <1404386897-27883-1-git-send-email-jerlbeck@sysmocom.de> References: <1404386897-27883-1-git-send-email-jerlbeck@sysmocom.de> Message-ID: <1404386897-27883-4-git-send-email-jerlbeck@sysmocom.de> This patch extends the BSSGP patch code to also patch LLC information elements along with MCC/MNC patching support for the following messages: - Attach Request - Attach Accept - Routing Area Update Request - Routing Area Update Accept - P-TMSI reallocation command Note that encrypted packets will not be patched. Ticket: OW#1185 Sponsored-by: On-Waves ehf --- openbsc/include/openbsc/gb_proxy.h | 10 ++ openbsc/src/gprs/gb_proxy.c | 281 +++++++++++++++++++++++++++++++++- openbsc/src/gprs/gb_proxy_vty.c | 34 ++++ openbsc/tests/gbproxy/gbproxy_test.ok | 24 +-- 4 files changed, 336 insertions(+), 13 deletions(-) diff --git a/openbsc/include/openbsc/gb_proxy.h b/openbsc/include/openbsc/gb_proxy.h index 220636e..7bac832 100644 --- a/openbsc/include/openbsc/gb_proxy.h +++ b/openbsc/include/openbsc/gb_proxy.h @@ -7,6 +7,15 @@ #include #include +enum gbproxy_patch_mode { + GBPROX_PATCH_DEFAULT, + GBPROX_PATCH_BSSGP, /*!< BSGGP messages only */ + GBPROX_PATCH_LLC_ATTACH_REQ, /*!< BSSGP and Attach Request */ + GBPROX_PATCH_LLC_ATTACH, /*!< BSSGP and Attach Request/Response */ + GBPROX_PATCH_LLC_GMM, /*!< BSSGP and all GMM msgs */ + GBPROX_PATCH_LLC, /*!< BSSGP and all supported LLC msgs */ +}; + struct gbproxy_config { /* parsed from config file */ uint16_t nsip_sgsn_nsei; @@ -17,6 +26,7 @@ struct gbproxy_config { /* force mcc/mnc */ int core_mnc; int core_mcc; + enum gbproxy_patch_mode patch_mode; }; extern struct gbproxy_config gbcfg; diff --git a/openbsc/src/gprs/gb_proxy.c b/openbsc/src/gprs/gb_proxy.c index 61059bb..5340c4d 100644 --- a/openbsc/src/gprs/gb_proxy.c +++ b/openbsc/src/gprs/gb_proxy.c @@ -61,6 +61,7 @@ enum gbprox_global_ctr { GBPROX_GLOB_CTR_OTHER_ERR, GBPROX_GLOB_CTR_RAID_PATCHED_BSS, GBPROX_GLOB_CTR_RAID_PATCHED_SGSN, + GBPROX_GLOB_CTR_PATCH_CRYPT_ERR, GBPROX_GLOB_CTR_PATCH_ERR, }; @@ -78,7 +79,8 @@ static const struct rate_ctr_desc global_ctr_description[] = { { "error", "Other error " }, { "raid-mod.bss", "RAID patched (BSS )" }, { "raid-mod.sgsn", "RAID patched (SGSN)" }, - { "mod-err", "Patching error " }, + { "mod-crypt-err", "Patch error: encrypted " }, + { "mod-err", "Patch error: other " }, }; static const struct rate_ctr_group_desc global_ctrg_desc = { @@ -346,6 +348,270 @@ static void gbprox_patch_raid(uint8_t *raid_enc, struct gbprox_patch_state *stat } } +static int gbprox_patch_gmm_attach_req(struct msgb *msg, + uint8_t *data, size_t data_len, + struct gbprox_patch_state *state, + int to_bss, int *len_change) +{ + /* Check minimum length, always includes the RAI */ + if (data_len < 23) + return 0; + + /* Skip MS network capability */ + if (data[0] < 1 || data[0] > 2) + /* invalid */ + return 0; + data_len -= data[0] + 1; + data += data[0] + 1; + + /* Skip Attach type */ + /* Skip Ciphering key sequence number */ + /* Skip DRX parameter */ + data_len -= 3; + data += 3; + + /* Skip Mobile identity */ + if (data[0] < 5 || data[0] > 8) + /* invalid */ + return 0; + data_len -= data[0] + 1; + data += data[0] + 1; + + gbprox_patch_raid(data, state, to_bss, "LLC/ATTACH_REQ"); + + return 1; +} + +static int gbprox_patch_gmm_attach_ack(struct msgb *msg, + uint8_t *data, size_t data_len, + struct gbprox_patch_state *state, + int to_bss, int *len_change) +{ + /* Check minimum length, always includes the RAI */ + if (data_len < 9) + return 0;; + + /* Skip Attach result */ + /* Skip Force to standby */ + /* Skip Periodic RA update timer */ + /* Skip Radio priority for SMS */ + /* Skip Spare half octet */ + data_len -= 3; + data += 3; + + gbprox_patch_raid(data, state, to_bss, "LLC/ATTACH_ACK"); + + return 1; +} + +static int gbprox_patch_gmm_ra_upd_req(struct msgb *msg, + uint8_t *data, size_t data_len, + struct gbprox_patch_state *state, + int to_bss, int *len_change) +{ + /* Check minimum length, always includes the RAI */ + if (data_len < 13) + return 0;; + + /* Skip Update type */ + /* Skip GPRS ciphering key sequence number */ + data_len -= 1; + data += 1; + + gbprox_patch_raid(data, state, to_bss, "LLC/RA_UPD_REQ"); + + return 1; +} + +static int gbprox_patch_gmm_ra_upd_ack(struct msgb *msg, + uint8_t *data, size_t data_len, + struct gbprox_patch_state *state, + int to_bss, int *len_change) +{ + /* Check minimum length, always includes the RAI */ + if (data_len < 8) + return 0;; + + /* Skip Force to standby */ + /* Skip Update result */ + /* Skip Periodic RA update timer */ + data_len -= 2; + data += 2; + + gbprox_patch_raid(data, state, to_bss, "LLC/RA_UPD_ACK"); + + return 1; +} + +static int gbprox_patch_gmm_ptmsi_reall_cmd(struct msgb *msg, + uint8_t *data, size_t data_len, + struct gbprox_patch_state *state, + int to_bss, int *len_change) +{ + /* Check minimum length, always includes the RAI */ + if (data_len < 12) + return 0;; + + /* Skip Allocated P-TMSI */ + if (data[0] != 5) + /* invalid */ + return 0;; + data_len -= 6; + data += 6; + + gbprox_patch_raid(data, state, to_bss, "LLC/PTMSI_REALL_CMD"); + + return 1; +} + +static int gbprox_patch_dtap(struct msgb *msg, uint8_t *data, size_t data_len, + struct gbprox_patch_state *state, + enum gbproxy_patch_mode patch_mode, int to_bss, + int *len_change) +{ + struct gsm48_hdr *g48h; + + *len_change = 0; + + if (data_len < 2) + return 0; + + g48h = (struct gsm48_hdr *)data; + + data += sizeof(struct gsm48_hdr); + data_len -= sizeof(struct gsm48_hdr); + + if ((g48h->proto_discr & 0x0f) != GSM48_PDISC_MM_GPRS && + (g48h->proto_discr & 0x0f) != GSM48_PDISC_SM_GPRS) + return 0; + + switch (g48h->msg_type) { + case GSM48_MT_GMM_ATTACH_REQ: + return gbprox_patch_gmm_attach_req(msg, data, data_len, + state, to_bss, len_change); + + case GSM48_MT_GMM_ATTACH_ACK: + if (patch_mode < GBPROX_PATCH_LLC_ATTACH) + break; + return gbprox_patch_gmm_attach_ack(msg, data, data_len, + state, to_bss, len_change); + + case GSM48_MT_GMM_RA_UPD_REQ: + if (patch_mode < GBPROX_PATCH_LLC_GMM) + break; + return gbprox_patch_gmm_ra_upd_req(msg, data, data_len, + state, to_bss, len_change); + + case GSM48_MT_GMM_RA_UPD_ACK: + if (patch_mode < GBPROX_PATCH_LLC_GMM) + break; + return gbprox_patch_gmm_ra_upd_ack(msg, data, data_len, + state, to_bss, len_change); + + case GSM48_MT_GMM_PTMSI_REALL_CMD: + if (patch_mode < GBPROX_PATCH_LLC_GMM) + break; + return gbprox_patch_gmm_ptmsi_reall_cmd(msg, data, data_len, + state, to_bss, len_change); + + default: + break; + }; + + return 0; +} + +static void gbprox_patch_llc(struct msgb *msg, uint8_t *llc, size_t llc_len, + struct gbprox_patch_state *state, + enum gbproxy_patch_mode patch_mode, int to_bss) +{ + struct gprs_llc_hdr_parsed ghp = {0}; + int rc; + uint8_t *data; + size_t data_len; + int fcs; + int len_change = 0; + const char *err_info = NULL; + int err_ctr = -1; + + /* parse LLC */ + rc = gprs_llc_hdr_parse(&ghp, llc, llc_len); + gprs_llc_hdr_dump(&ghp); + if (rc != 0) { + LOGP(DLLC, LOGL_NOTICE, "Error during LLC header parsing\n"); + return; + } + + fcs = gprs_llc_fcs(llc, ghp.crc_length); + LOGP(DLLC, LOGL_DEBUG, "Got LLC message, CRC: %06x (computed %06x)\n", + ghp.fcs, fcs); + + if (!ghp.data) + return; + + if (ghp.sapi != GPRS_SAPI_GMM) + return; + + if (ghp.cmd != GPRS_LLC_UI) + return; + + if (ghp.is_encrypted) { + if (gbcfg.patch_mode > GBPROX_PATCH_LLC_ATTACH_REQ) { + /* LLC patch (GMM) has been requested explicitely */ + err_info = "GMM message is encrypted"; + err_ctr = GBPROX_GLOB_CTR_PATCH_CRYPT_ERR; + goto patch_error; + } + + return; + } + + /* fix DTAP GMM/GSM */ + data = ghp.data; + data_len = ghp.data_len; + + rc = gbprox_patch_dtap(msg, data, data_len, state, patch_mode, to_bss, + &len_change); + + if (rc > 0) { + llc_len += len_change; + ghp.crc_length += len_change; + + /* Fix LLC IE len */ + if (llc[-2] == BSSGP_IE_LLC_PDU && llc[-1] & 0x80) { + /* most probably a one byte length */ + if (llc_len > 127) { + err_info = "Cannot increase size"; + err_ctr = GBPROX_GLOB_CTR_PATCH_ERR; + goto patch_error; + } + llc[-1] = llc_len | 0x80; + } else { + llc[-2] = (llc_len >> 8) & 0x7f; + llc[-1] = llc_len & 0xff; + } + + /* Fix FCS */ + fcs = gprs_llc_fcs(llc, ghp.crc_length); + LOGP(DLLC, LOGL_DEBUG, "Updated LLC message, CRC: %06x -> %06x\n", + ghp.fcs, fcs); + + llc[llc_len - 3] = fcs & 0xff; + llc[llc_len - 2] = (fcs >> 8) & 0xff; + llc[llc_len - 1] = (fcs >> 16) & 0xff; + } + + return; + +patch_error: + OSMO_ASSERT(err_ctr >= 0); + rate_ctr_inc(&get_global_ctrg()->ctr[err_ctr]); + LOGP(DGPRS, LOGL_ERROR, + "Failed to patch BSSGP/GMM message as requested: %s.\n", err_info); + + return; +} + /* patch BSSGP message to use core_mcc/mnc on the SGSN side */ static void gbprox_patch_bssgp_message(struct msgb *msg, int to_bss) { @@ -356,6 +622,7 @@ static void gbprox_patch_bssgp_message(struct msgb *msg, int to_bss) struct gbprox_patch_state *state = &gbprox_patch_state; uint8_t *data; size_t data_len; + enum gbproxy_patch_mode patch_mode; if (!gbcfg.core_mcc && !gbcfg.core_mnc) return; @@ -363,6 +630,9 @@ static void gbprox_patch_bssgp_message(struct msgb *msg, int to_bss) bgph = (struct bssgp_normal_hdr *) msgb_bssgph(msg); budh = (struct bssgp_ud_hdr *) msgb_bssgph(msg); pdu_type = bgph->pdu_type; + patch_mode = gbcfg.patch_mode; + if (patch_mode == GBPROX_PATCH_DEFAULT) + patch_mode = GBPROX_PATCH_LLC; if (to_bss && !state->local_mcc && !state->local_mnc) return; @@ -386,6 +656,15 @@ static void gbprox_patch_bssgp_message(struct msgb *msg, int to_bss) if (TLVP_PRESENT(&tp, BSSGP_IE_CELL_ID)) gbprox_patch_raid((uint8_t *)TLVP_VAL(&tp, BSSGP_IE_CELL_ID), state, to_bss, "CELL_ID"); + + if (TLVP_PRESENT(&tp, BSSGP_IE_LLC_PDU) && + patch_mode >= GBPROX_PATCH_LLC_ATTACH_REQ) { + uint8_t *llc = (uint8_t *)TLVP_VAL(&tp, BSSGP_IE_LLC_PDU); + size_t llc_len = TLVP_LEN(&tp, BSSGP_IE_LLC_PDU); + gbprox_patch_llc(msg, llc, llc_len, state, patch_mode, to_bss); + /* Note that the tp struct might contain invalid pointers here + * if the LLC field has changed its size */ + } } /* feed a message down the NS-VC associated with the specified peer */ diff --git a/openbsc/src/gprs/gb_proxy_vty.c b/openbsc/src/gprs/gb_proxy_vty.c index acd8051..06f8082 100644 --- a/openbsc/src/gprs/gb_proxy_vty.c +++ b/openbsc/src/gprs/gb_proxy_vty.c @@ -44,6 +44,16 @@ static struct cmd_node gbproxy_node = { 1, }; +static const struct value_string patch_modes[] = { + {GBPROX_PATCH_DEFAULT, "default"}, + {GBPROX_PATCH_BSSGP, "bssgp"}, + {GBPROX_PATCH_LLC_ATTACH_REQ, "llc-attach-req"}, + {GBPROX_PATCH_LLC_ATTACH, "llc-attach"}, + {GBPROX_PATCH_LLC_GMM, "llc-gmm"}, + {GBPROX_PATCH_LLC, "llc"}, + {0, NULL} +}; + static int config_write_gbproxy(struct vty *vty) { vty_out(vty, "gbproxy%s", VTY_NEWLINE); @@ -58,6 +68,11 @@ static int config_write_gbproxy(struct vty *vty) vty_out(vty, " core-mobile-network-code %d%s", g_cfg->core_mnc, VTY_NEWLINE); + if (g_cfg->patch_mode != GBPROX_PATCH_DEFAULT) + vty_out(vty, " patch-mode %s%s", + get_value_string(patch_modes, g_cfg->patch_mode), + VTY_NEWLINE); + return CMD_SUCCESS; } @@ -123,6 +138,24 @@ DEFUN(cfg_gbproxy_no_core_mcc, return CMD_SUCCESS; } +DEFUN(cfg_gbproxy_patch_mode, + cfg_gbproxy_patch_mode_cmd, + "patch-mode (default|bssgp|llc-attach-req|llc-attach|llc)", + "Set patch mode\n" + "Use build-in default (at least llc-attach-req)\n" + "Only patch BSSGP headers\n" + "Patch BSSGP headers and LLC Attach Request messages\n" + "Patch BSSGP headers and LLC Attach Request/Accept messages\n" + "Patch BSSGP headers and all supported GMM LLC messages\n" + ) +{ + int val = get_string_value(patch_modes, argv[0]); + OSMO_ASSERT(val >= 0); + g_cfg->patch_mode = val; + return CMD_SUCCESS; +} + + int gbproxy_vty_init(void) { @@ -139,6 +172,7 @@ int gbproxy_vty_init(void) install_element(GBPROXY_NODE, &cfg_gbproxy_core_mnc_cmd); install_element(GBPROXY_NODE, &cfg_gbproxy_no_core_mcc_cmd); install_element(GBPROXY_NODE, &cfg_gbproxy_no_core_mnc_cmd); + install_element(GBPROXY_NODE, &cfg_gbproxy_patch_mode_cmd); return 0; } diff --git a/openbsc/tests/gbproxy/gbproxy_test.ok b/openbsc/tests/gbproxy/gbproxy_test.ok index f8bd1e7..d3de445 100644 --- a/openbsc/tests/gbproxy/gbproxy_test.ok +++ b/openbsc/tests/gbproxy/gbproxy_test.ok @@ -1677,10 +1677,10 @@ CALLBACK, event 0, msg length 75, bvci 0x1002 01 bb c5 46 79 00 00 04 08 88 11 22 33 40 50 60 75 30 00 80 0e 00 34 01 c0 01 08 01 02 f5 e0 21 08 02 05 f4 fb c5 46 79 11 22 33 40 50 60 19 18 b3 43 2b 25 96 62 00 60 80 9a c2 c6 62 00 60 80 ba c8 c6 62 00 60 80 00 16 6d 01 NS UNITDATA MESSAGE to SGSN, BVCI 0x1002, msg length 75 -01 bb c5 46 79 00 00 04 08 88 21 63 54 40 50 60 75 30 00 80 0e 00 34 01 c0 01 08 01 02 f5 e0 21 08 02 05 f4 fb c5 46 79 11 22 33 40 50 60 19 18 b3 43 2b 25 96 62 00 60 80 9a c2 c6 62 00 60 80 ba c8 c6 62 00 60 80 00 16 6d 01 +01 bb c5 46 79 00 00 04 08 88 21 63 54 40 50 60 75 30 00 80 0e 00 34 01 c0 01 08 01 02 f5 e0 21 08 02 05 f4 fb c5 46 79 21 63 54 40 50 60 19 18 b3 43 2b 25 96 62 00 60 80 9a c2 c6 62 00 60 80 ba c8 c6 62 00 60 80 00 8e cd 32 MESSAGE to SGSN at 0x05060708:32000, msg length 79 -00 00 10 02 01 bb c5 46 79 00 00 04 08 88 21 63 54 40 50 60 75 30 00 80 0e 00 34 01 c0 01 08 01 02 f5 e0 21 08 02 05 f4 fb c5 46 79 11 22 33 40 50 60 19 18 b3 43 2b 25 96 62 00 60 80 9a c2 c6 62 00 60 80 ba c8 c6 62 00 60 80 00 16 6d 01 +00 00 10 02 01 bb c5 46 79 00 00 04 08 88 21 63 54 40 50 60 75 30 00 80 0e 00 34 01 c0 01 08 01 02 f5 e0 21 08 02 05 f4 fb c5 46 79 21 63 54 40 50 60 19 18 b3 43 2b 25 96 62 00 60 80 9a c2 c6 62 00 60 80 ba c8 c6 62 00 60 80 00 8e cd 32 result (UNITDATA) = 79 @@ -1691,10 +1691,10 @@ CALLBACK, event 0, msg length 88, bvci 0x1002 00 bb c5 46 79 00 50 20 16 82 02 58 13 99 18 b3 43 2b 25 96 62 00 60 80 9a c2 c6 62 00 60 80 ba c8 c6 62 00 60 80 00 0a 82 08 02 0d 88 11 12 13 14 15 16 17 18 00 81 00 0e 9e 41 c0 05 08 02 01 49 04 21 63 54 40 50 60 19 cd d7 08 17 16 18 05 f4 fb c5 47 22 42 67 9a NS UNITDATA MESSAGE to BSS, BVCI 0x1002, msg length 88 -00 bb c5 46 79 00 50 20 16 82 02 58 13 99 18 b3 43 2b 25 96 62 00 60 80 9a c2 c6 62 00 60 80 ba c8 c6 62 00 60 80 00 0a 82 08 02 0d 88 11 12 13 14 15 16 17 18 00 81 00 0e 9e 41 c0 05 08 02 01 49 04 21 63 54 40 50 60 19 cd d7 08 17 16 18 05 f4 fb c5 47 22 42 67 9a +00 bb c5 46 79 00 50 20 16 82 02 58 13 99 18 b3 43 2b 25 96 62 00 60 80 9a c2 c6 62 00 60 80 ba c8 c6 62 00 60 80 00 0a 82 08 02 0d 88 11 12 13 14 15 16 17 18 00 81 00 0e 9e 41 c0 05 08 02 01 49 04 11 22 33 40 50 60 19 cd d7 08 17 16 18 05 f4 fb c5 47 22 af 3d ab MESSAGE to BSS at 0x01020304:1111, msg length 92 -00 00 10 02 00 bb c5 46 79 00 50 20 16 82 02 58 13 99 18 b3 43 2b 25 96 62 00 60 80 9a c2 c6 62 00 60 80 ba c8 c6 62 00 60 80 00 0a 82 08 02 0d 88 11 12 13 14 15 16 17 18 00 81 00 0e 9e 41 c0 05 08 02 01 49 04 21 63 54 40 50 60 19 cd d7 08 17 16 18 05 f4 fb c5 47 22 42 67 9a +00 00 10 02 00 bb c5 46 79 00 50 20 16 82 02 58 13 99 18 b3 43 2b 25 96 62 00 60 80 9a c2 c6 62 00 60 80 ba c8 c6 62 00 60 80 00 0a 82 08 02 0d 88 11 12 13 14 15 16 17 18 00 81 00 0e 9e 41 c0 05 08 02 01 49 04 11 22 33 40 50 60 19 cd d7 08 17 16 18 05 f4 fb c5 47 22 af 3d ab result (UNITDATA) = 92 @@ -1705,10 +1705,10 @@ CALLBACK, event 0, msg length 85, bvci 0x1002 01 af e2 80 6e 00 00 04 08 88 11 22 33 40 50 60 70 80 00 80 0e 00 3e 01 c0 15 08 08 10 11 22 33 40 50 60 1d 19 13 42 33 57 2b f7 c8 48 02 13 48 50 c8 48 02 14 48 50 c8 48 02 17 49 10 c8 48 02 00 19 8b b2 92 17 16 27 07 04 31 02 e5 e0 32 02 20 00 96 3e 97 NS UNITDATA MESSAGE to SGSN, BVCI 0x1002, msg length 85 -01 af e2 80 6e 00 00 04 08 88 21 63 54 40 50 60 70 80 00 80 0e 00 3e 01 c0 15 08 08 10 11 22 33 40 50 60 1d 19 13 42 33 57 2b f7 c8 48 02 13 48 50 c8 48 02 14 48 50 c8 48 02 17 49 10 c8 48 02 00 19 8b b2 92 17 16 27 07 04 31 02 e5 e0 32 02 20 00 96 3e 97 +01 af e2 80 6e 00 00 04 08 88 21 63 54 40 50 60 70 80 00 80 0e 00 3e 01 c0 15 08 08 10 21 63 54 40 50 60 1d 19 13 42 33 57 2b f7 c8 48 02 13 48 50 c8 48 02 14 48 50 c8 48 02 17 49 10 c8 48 02 00 19 8b b2 92 17 16 27 07 04 31 02 e5 e0 32 02 20 00 1d f0 41 MESSAGE to SGSN at 0x05060708:32000, msg length 89 -00 00 10 02 01 af e2 80 6e 00 00 04 08 88 21 63 54 40 50 60 70 80 00 80 0e 00 3e 01 c0 15 08 08 10 11 22 33 40 50 60 1d 19 13 42 33 57 2b f7 c8 48 02 13 48 50 c8 48 02 14 48 50 c8 48 02 17 49 10 c8 48 02 00 19 8b b2 92 17 16 27 07 04 31 02 e5 e0 32 02 20 00 96 3e 97 +00 00 10 02 01 af e2 80 6e 00 00 04 08 88 21 63 54 40 50 60 70 80 00 80 0e 00 3e 01 c0 15 08 08 10 21 63 54 40 50 60 1d 19 13 42 33 57 2b f7 c8 48 02 13 48 50 c8 48 02 14 48 50 c8 48 02 17 49 10 c8 48 02 00 19 8b b2 92 17 16 27 07 04 31 02 e5 e0 32 02 20 00 1d f0 41 result (UNITDATA) = 89 @@ -1719,10 +1719,10 @@ CALLBACK, event 0, msg length 91, bvci 0x1002 00 af e2 80 6e 00 50 20 16 82 02 58 13 9d 19 13 42 33 57 2b f7 c8 48 02 13 48 50 c8 48 02 14 48 50 c8 48 02 17 49 10 c8 48 02 00 0a 82 07 04 0d 88 11 12 13 14 15 16 17 18 00 81 00 0e 9d 41 c0 19 08 09 00 49 21 63 54 40 50 60 19 54 ab b3 18 05 f4 ef e2 81 17 17 16 c3 bf cc NS UNITDATA MESSAGE to BSS, BVCI 0x1002, msg length 91 -00 af e2 80 6e 00 50 20 16 82 02 58 13 9d 19 13 42 33 57 2b f7 c8 48 02 13 48 50 c8 48 02 14 48 50 c8 48 02 17 49 10 c8 48 02 00 0a 82 07 04 0d 88 11 12 13 14 15 16 17 18 00 81 00 0e 9d 41 c0 19 08 09 00 49 21 63 54 40 50 60 19 54 ab b3 18 05 f4 ef e2 81 17 17 16 c3 bf cc +00 af e2 80 6e 00 50 20 16 82 02 58 13 9d 19 13 42 33 57 2b f7 c8 48 02 13 48 50 c8 48 02 14 48 50 c8 48 02 17 49 10 c8 48 02 00 0a 82 07 04 0d 88 11 12 13 14 15 16 17 18 00 81 00 0e 9d 41 c0 19 08 09 00 49 11 22 33 40 50 60 19 54 ab b3 18 05 f4 ef e2 81 17 17 16 2e e5 fd MESSAGE to BSS at 0x01020304:1111, msg length 95 -00 00 10 02 00 af e2 80 6e 00 50 20 16 82 02 58 13 9d 19 13 42 33 57 2b f7 c8 48 02 13 48 50 c8 48 02 14 48 50 c8 48 02 17 49 10 c8 48 02 00 0a 82 07 04 0d 88 11 12 13 14 15 16 17 18 00 81 00 0e 9d 41 c0 19 08 09 00 49 21 63 54 40 50 60 19 54 ab b3 18 05 f4 ef e2 81 17 17 16 c3 bf cc +00 00 10 02 00 af e2 80 6e 00 50 20 16 82 02 58 13 9d 19 13 42 33 57 2b f7 c8 48 02 13 48 50 c8 48 02 14 48 50 c8 48 02 17 49 10 c8 48 02 00 0a 82 07 04 0d 88 11 12 13 14 15 16 17 18 00 81 00 0e 9d 41 c0 19 08 09 00 49 11 22 33 40 50 60 19 54 ab b3 18 05 f4 ef e2 81 17 17 16 2e e5 fd result (UNITDATA) = 95 @@ -1755,8 +1755,8 @@ MESSAGE to SGSN at 0x05060708:32000, msg length 80 result (UNITDATA) = 80 Gbproxy global: - RAID patched (BSS ): 6 - RAID patched (SGSN): 1 + RAID patched (BSS ): 8 + RAID patched (SGSN): 3 Peers: NSEI 4096, BVCI 4098, not blocked, RAI 112-332-16464-96 --- Bad cases --- @@ -1786,8 +1786,8 @@ result (BVC_SUSPEND_ACK) = 28 Gbproxy global: Invalid BVC Identifier : 1 Invalid Routing Area Identifier : 1 - RAID patched (BSS ): 6 - RAID patched (SGSN): 2 + RAID patched (BSS ): 8 + RAID patched (SGSN): 4 Peers: NSEI 4096, BVCI 4098, not blocked, RAI 112-332-16464-96 ===== GbProxy test END -- 1.9.1 From holger at freyther.de Mon Jul 7 18:28:14 2014 From: holger at freyther.de (Holger Hans Peter Freyther) Date: Mon, 7 Jul 2014 20:28:14 +0200 Subject: [PATCH 4/6] gprs: Add MCC/MNC patch support for LLC/GMM messages In-Reply-To: <1404386897-27883-4-git-send-email-jerlbeck@sysmocom.de> References: <1404386897-27883-1-git-send-email-jerlbeck@sysmocom.de> <1404386897-27883-4-git-send-email-jerlbeck@sysmocom.de> Message-ID: <20140707182814.GB11978@xiaoyu.lan> On Thu, Jul 03, 2014 at 01:28:15PM +0200, Jacob Erlbeck wrote: > + /* Skip Attach result */ > + /* Skip Force to standby */ > + /* Skip Periodic RA update timer */ > + /* Skip Radio priority for SMS */ > + /* Skip Spare half octet */ > + data_len -= 3; > + data += 3; Which are the other half octets here? > + /* Skip Update type */ > + /* Skip GPRS ciphering key sequence number */ > + data_len -= 1; > + data += 1; I don't have a copy of the specification open right now. Could you please indicate how the number of skips relate to data_len/data adjustments here? > + if (data[0] != 5) > + /* invalid */ > + return 0;; Extra ';' :) > + /* LLC patch (GMM) has been requested explicitely */ ^-- typo > + /* Fix LLC IE len */ > + if (llc[-2] == BSSGP_IE_LLC_PDU && llc[-1] & 0x80) { > + /* most probably a one byte length */ You mentioned this to me already. What API documentation do you need? Keep track inside the tlv_parsed structure of _where_ the tag started? > + patch_mode = gbcfg.patch_mode; > + if (patch_mode == GBPROX_PATCH_DEFAULT) > + patch_mode = GBPROX_PATCH_LLC; I am thinking of the "gbcfg.patch_mode > GBPROX_PATCH_LLC_ATTACH_REQ". So we are lucky as default is < GBPROX_PATCH_LLC_ATTACH_REQ right now. Wouldn't it be better to not access gbcfg.patch_mode directly and do the "default" handling inside this method? From jerlbeck at sysmocom.de Thu Jul 3 11:28:16 2014 From: jerlbeck at sysmocom.de (Jacob Erlbeck) Date: Thu, 3 Jul 2014 13:28:16 +0200 Subject: [PATCH 5/6] gprs: Add APN patch support for LLC/GSM messages In-Reply-To: <1404386897-27883-1-git-send-email-jerlbeck@sysmocom.de> References: <1404386897-27883-1-git-send-email-jerlbeck@sysmocom.de> Message-ID: <1404386897-27883-5-git-send-email-jerlbeck@sysmocom.de> Patch the APN in every 'Activate PDP Context Request' message to the value given by the 'core-access-point-name' command. If the command is given without an APN, the whole APN IE will be removed. If the command is being prefixed by a 'no', APN IE remain unmodified. The patch mode 'llc-gsm' is added to selectively enable the patching of LLC session management messages. This is enabled implicitely by the patch mode 'llc'. Note that the patch mode should not be set to a value not enabling the patching of LLC GSM messages ('llc-gsm', 'llc', and 'default' are sufficient to patch 'Activate PDP Context Request' messages). Ticket: OW#1192 Sponsored-by: On-Waves ehf --- openbsc/include/openbsc/gb_proxy.h | 6 ++ openbsc/src/gprs/gb_proxy.c | 198 +++++++++++++++++++++++++++++++++- openbsc/src/gprs/gb_proxy_vty.c | 69 +++++++++++- openbsc/tests/gbproxy/gbproxy_test.c | 5 +- openbsc/tests/gbproxy/gbproxy_test.ok | 22 ++-- 5 files changed, 285 insertions(+), 15 deletions(-) diff --git a/openbsc/include/openbsc/gb_proxy.h b/openbsc/include/openbsc/gb_proxy.h index 7bac832..2ecd49f 100644 --- a/openbsc/include/openbsc/gb_proxy.h +++ b/openbsc/include/openbsc/gb_proxy.h @@ -13,6 +13,7 @@ enum gbproxy_patch_mode { GBPROX_PATCH_LLC_ATTACH_REQ, /*!< BSSGP and Attach Request */ GBPROX_PATCH_LLC_ATTACH, /*!< BSSGP and Attach Request/Response */ GBPROX_PATCH_LLC_GMM, /*!< BSSGP and all GMM msgs */ + GBPROX_PATCH_LLC_GSM, /*!< BSSGP and all GMM and GSM msgs */ GBPROX_PATCH_LLC, /*!< BSSGP and all supported LLC msgs */ }; @@ -26,6 +27,8 @@ struct gbproxy_config { /* force mcc/mnc */ int core_mnc; int core_mcc; + uint8_t* core_apn; + size_t core_apn_size; enum gbproxy_patch_mode patch_mode; }; @@ -54,4 +57,7 @@ int gbprox_reset_persistent_nsvcs(struct gprs_ns_inst *nsi); int gbprox_dump_global(FILE *stream, int indent, int verbose); int gbprox_dump_peers(FILE *stream, int indent, int verbose); void gbprox_reset(); + +char *gbprox_apn_to_str(char *str, const uint8_t *apn_enc, size_t max_chars); +int gbprox_str_to_apn(uint8_t *apn_enc, const char *str, size_t max_chars); #endif diff --git a/openbsc/src/gprs/gb_proxy.c b/openbsc/src/gprs/gb_proxy.c index 5340c4d..ea590b3 100644 --- a/openbsc/src/gprs/gb_proxy.c +++ b/openbsc/src/gprs/gb_proxy.c @@ -61,6 +61,7 @@ enum gbprox_global_ctr { GBPROX_GLOB_CTR_OTHER_ERR, GBPROX_GLOB_CTR_RAID_PATCHED_BSS, GBPROX_GLOB_CTR_RAID_PATCHED_SGSN, + GBPROX_GLOB_CTR_APN_PATCHED, GBPROX_GLOB_CTR_PATCH_CRYPT_ERR, GBPROX_GLOB_CTR_PATCH_ERR, }; @@ -79,6 +80,7 @@ static const struct rate_ctr_desc global_ctr_description[] = { { "error", "Other error " }, { "raid-mod.bss", "RAID patched (BSS )" }, { "raid-mod.sgsn", "RAID patched (SGSN)" }, + { "apn-mod.sgsn", "APN patched " }, { "mod-crypt-err", "Patch error: encrypted " }, { "mod-err", "Patch error: other " }, }; @@ -277,6 +279,89 @@ static void strip_ns_hdr(struct msgb *msg) msgb_pull(msg, strip_len); } +/* TODO: Move this to libosmocore/msgb.c */ +static int msgb_resize_area(struct msgb *msg, uint8_t *area, + size_t old_size, size_t new_size) +{ + int rc; + uint8_t *rest = area + old_size; + int rest_len = msg->len - old_size - (area - msg->data); + int delta_size = (int)new_size - (int)old_size; + + if (delta_size == 0) + return 0; + + if (delta_size > 0) { + rc = msgb_trim(msg, msg->len + delta_size); + if (rc < 0) + return rc; + } + + memmove(area + new_size, area + old_size, rest_len); + + if (msg->l1h >= rest) + msg->l1h += delta_size; + if (msg->l2h >= rest) + msg->l2h += delta_size; + if (msg->l3h >= rest) + msg->l3h += delta_size; + if (msg->l4h >= rest) + msg->l4h += delta_size; + + if (delta_size < 0) + msgb_trim(msg, msg->len + delta_size); + + return 0; +} + +/* TODO: Move these conversion functions to a utils file. */ +char * gbprox_apn_to_str(char *out_str, const uint8_t *apn_enc, size_t rest_chars) +{ + char *str = out_str; + + while (rest_chars > 0 && apn_enc[0]) { + size_t label_size = apn_enc[0]; + if (label_size + 1 > rest_chars) + return NULL; + + memmove(str, apn_enc + 1, label_size); + str += label_size; + rest_chars -= label_size + 1; + apn_enc += label_size + 1; + + if (rest_chars) + *(str++) = '.'; + } + str[0] = '\0'; + + return out_str; +} + +int gbprox_str_to_apn(uint8_t *apn_enc, const char *str, size_t max_chars) +{ + uint8_t *last_len_field = apn_enc; + int len = 1; + apn_enc += 1; + + while (str[0]) { + if (str[0] == '.') { + *last_len_field = (apn_enc - last_len_field) - 1; + last_len_field = apn_enc; + } else { + *apn_enc = str[0]; + } + apn_enc += 1; + str += 1; + len += 1; + if (len > max_chars) + return -1; + } + + *last_len_field = (apn_enc - last_len_field) - 1; + + return len; +} + /* patch RA identifier in place, update peer accordingly */ static void gbprox_patch_raid(uint8_t *raid_enc, struct gbprox_patch_state *state, int to_bss, const char *log_text) @@ -348,6 +433,56 @@ static void gbprox_patch_raid(uint8_t *raid_enc, struct gbprox_patch_state *stat } } +static void gbprox_patch_apn_ie(struct msgb *msg, + uint8_t *apn_ie, size_t apn_ie_len, + size_t *new_apn_ie_len, const char *log_text) +{ + struct apn_ie_hdr { + uint8_t iei; + uint8_t apn_len; + uint8_t apn[0]; + } *hdr = (void *)apn_ie; + + size_t apn_len = hdr->apn_len; + uint8_t *apn = hdr->apn; + + OSMO_ASSERT(apn_ie_len == apn_len + sizeof(struct apn_ie_hdr)); + OSMO_ASSERT(apn_ie_len > 2 && apn_ie_len <= 102); + + if (gbcfg.core_apn_size == 0) { + char str1[110]; + /* Remove the IE */ + LOGP(DGPRS, LOGL_DEBUG, + "Patching %s to SGSN: Removing APN '%s'\n", + log_text, + gbprox_apn_to_str(str1, apn, apn_len)); + + *new_apn_ie_len = 0; + msgb_resize_area(msg, apn_ie, apn_ie_len, 0); + } else { + /* Resize the IE */ + char str1[110]; + char str2[110]; + + OSMO_ASSERT(gbcfg.core_apn_size <= 100); + + LOGP(DGPRS, LOGL_DEBUG, + "Patching %s to SGSN: " + "Replacing APN '%s' -> '%s'\n", + log_text, + gbprox_apn_to_str(str1, apn, apn_len), + gbprox_apn_to_str(str2, gbcfg.core_apn, + gbcfg.core_apn_size)); + + *new_apn_ie_len = gbcfg.core_apn_size + 2; + msgb_resize_area(msg, apn, apn_len, gbcfg.core_apn_size); + memcpy(apn, gbcfg.core_apn, gbcfg.core_apn_size); + hdr->apn_len = gbcfg.core_apn_size; + } + + rate_ctr_inc(&get_global_ctrg()->ctr[GBPROX_GLOB_CTR_APN_PATCHED]); +} + static int gbprox_patch_gmm_attach_req(struct msgb *msg, uint8_t *data, size_t data_len, struct gbprox_patch_state *state, @@ -464,6 +599,60 @@ static int gbprox_patch_gmm_ptmsi_reall_cmd(struct msgb *msg, return 1; } +static int gbprox_patch_gsm_act_pdp_req(struct msgb *msg, + uint8_t *data, size_t data_len, + struct gbprox_patch_state *state, + int to_bss, int *len_change) +{ + size_t new_len, old_len; + + /* Check minimum length, always contains length field of + * Requested QoS */ + if (data_len < 9) + return 0; + + /* Skip Requested NSAPI */ + /* Skip Requested LLC SAPI */ + data_len -= 2; + data += 2; + + /* Skip Requested QoS (support 04.08 and 24.008) */ + if (data[0] < 4 || data[0] > 14 || + data_len - (data[0] + 1) < 0) + /* invalid */ + return 0; + data_len -= data[0] + 1; + data += data[0] + 1; + + /* Skip Requested PDP address */ + if (data_len < 1 || + data[0] < 2 || data[0] > 18 || + data_len - (data[0] + 1) < 0) + /* invalid */ + return 0; + data_len -= data[0] + 1; + data += data[0] + 1; + + /* Access point name */ + if (data_len < 2 || data[0] != GSM48_IE_GSM_APN) + return 0; + + if (data[1] < 1 || data[1] > 100 || + data_len - (data[1] + 2) < 0) + /* invalid */ + return 0; + + old_len = data[1] + 2; + + gbprox_patch_apn_ie(msg, data, old_len, &new_len, "LLC/ACT_PDP_REQ"); + + *len_change += (int)new_len - (int)old_len; + data_len -= old_len; + data += new_len; + + return 1; +} + static int gbprox_patch_dtap(struct msgb *msg, uint8_t *data, size_t data_len, struct gbprox_patch_state *state, enum gbproxy_patch_mode patch_mode, int to_bss, @@ -514,6 +703,13 @@ static int gbprox_patch_dtap(struct msgb *msg, uint8_t *data, size_t data_len, return gbprox_patch_gmm_ptmsi_reall_cmd(msg, data, data_len, state, to_bss, len_change); + case GSM48_MT_GSM_ACT_PDP_REQ: + if (patch_mode < GBPROX_PATCH_LLC_GSM) + break; + if (gbcfg.core_apn == NULL) + break; + return gbprox_patch_gsm_act_pdp_req(msg, data, data_len, + state, to_bss, len_change); default: break; }; @@ -624,7 +820,7 @@ static void gbprox_patch_bssgp_message(struct msgb *msg, int to_bss) size_t data_len; enum gbproxy_patch_mode patch_mode; - if (!gbcfg.core_mcc && !gbcfg.core_mnc) + if (!gbcfg.core_mcc && !gbcfg.core_mnc && !gbcfg.core_apn) return; bgph = (struct bssgp_normal_hdr *) msgb_bssgph(msg); diff --git a/openbsc/src/gprs/gb_proxy_vty.c b/openbsc/src/gprs/gb_proxy_vty.c index 06f8082..8d3ff25 100644 --- a/openbsc/src/gprs/gb_proxy_vty.c +++ b/openbsc/src/gprs/gb_proxy_vty.c @@ -21,6 +21,7 @@ #include #include #include +#include #include @@ -50,6 +51,7 @@ static const struct value_string patch_modes[] = { {GBPROX_PATCH_LLC_ATTACH_REQ, "llc-attach-req"}, {GBPROX_PATCH_LLC_ATTACH, "llc-attach"}, {GBPROX_PATCH_LLC_GMM, "llc-gmm"}, + {GBPROX_PATCH_LLC_GSM, "llc-gsm"}, {GBPROX_PATCH_LLC, "llc"}, {0, NULL} }; @@ -67,6 +69,18 @@ static int config_write_gbproxy(struct vty *vty) if (g_cfg->core_mnc > 0) vty_out(vty, " core-mobile-network-code %d%s", g_cfg->core_mnc, VTY_NEWLINE); + if (g_cfg->core_apn != NULL) { + if (g_cfg->core_apn_size > 0) { + char str[500] = {0}; + vty_out(vty, " core-access-point-name %s%s", + gbprox_apn_to_str(str, g_cfg->core_apn, + g_cfg->core_apn_size), + VTY_NEWLINE); + } else { + vty_out(vty, " core-access-point-name%s", + VTY_NEWLINE); + } + } if (g_cfg->patch_mode != GBPROX_PATCH_DEFAULT) vty_out(vty, " patch-mode %s%s", @@ -138,15 +152,61 @@ DEFUN(cfg_gbproxy_no_core_mcc, return CMD_SUCCESS; } +#define GBPROXY_CORE_APN_STR "Use this access point name (APN) for the backbone\n" + +DEFUN(cfg_gbproxy_core_apn_remove, + cfg_gbproxy_core_apn_remove_cmd, + "core-access-point-name", + GBPROXY_CORE_APN_STR) +{ + talloc_free(g_cfg->core_apn); + /* TODO: replace NULL */ + g_cfg->core_apn = talloc_zero_size(NULL, 2); + g_cfg->core_apn_size = 0; + return CMD_SUCCESS; +} + +DEFUN(cfg_gbproxy_core_apn, + cfg_gbproxy_core_apn_cmd, + "core-access-point-name APN", + GBPROXY_CORE_APN_STR "Replacement APN\n") +{ + int apn_len = strlen(argv[0]) + 1; + + if (apn_len > 100) { + vty_out(vty, "APN string too long (max 99 chars)%s", + VTY_NEWLINE); + return CMD_WARNING; + } + + /* TODO: replace NULL */ + g_cfg->core_apn = talloc_realloc_size(NULL, g_cfg->core_apn, apn_len); + g_cfg->core_apn_size = gbprox_str_to_apn(g_cfg->core_apn, argv[0], apn_len); + + return CMD_SUCCESS; +} + +DEFUN(cfg_gbproxy_no_core_apn, + cfg_gbproxy_no_core_apn_cmd, + "no core-access-point-name", + NO_STR GBPROXY_CORE_APN_STR) +{ + talloc_free(g_cfg->core_apn); + g_cfg->core_apn = NULL; + return CMD_SUCCESS; +} + DEFUN(cfg_gbproxy_patch_mode, cfg_gbproxy_patch_mode_cmd, - "patch-mode (default|bssgp|llc-attach-req|llc-attach|llc)", + "patch-mode (default|bssgp|llc-attach-req|llc-attach|llc-gmm|llc-gsm|llc)", "Set patch mode\n" - "Use build-in default (at least llc-attach-req)\n" + "Use build-in default (best effort, try to patch everything)\n" "Only patch BSSGP headers\n" "Patch BSSGP headers and LLC Attach Request messages\n" "Patch BSSGP headers and LLC Attach Request/Accept messages\n" - "Patch BSSGP headers and all supported GMM LLC messages\n" + "Patch BSSGP headers and LLC GMM messages\n" + "Patch BSSGP headers, LLC GMM, and LLC GSM messages\n" + "Patch BSSGP headers and all supported LLC messages\n" ) { int val = get_string_value(patch_modes, argv[0]); @@ -170,8 +230,11 @@ int gbproxy_vty_init(void) install_element(GBPROXY_NODE, &cfg_nsip_sgsn_nsei_cmd); install_element(GBPROXY_NODE, &cfg_gbproxy_core_mcc_cmd); install_element(GBPROXY_NODE, &cfg_gbproxy_core_mnc_cmd); + install_element(GBPROXY_NODE, &cfg_gbproxy_core_apn_remove_cmd); + install_element(GBPROXY_NODE, &cfg_gbproxy_core_apn_cmd); install_element(GBPROXY_NODE, &cfg_gbproxy_no_core_mcc_cmd); install_element(GBPROXY_NODE, &cfg_gbproxy_no_core_mnc_cmd); + install_element(GBPROXY_NODE, &cfg_gbproxy_no_core_apn_cmd); install_element(GBPROXY_NODE, &cfg_gbproxy_patch_mode_cmd); return 0; diff --git a/openbsc/tests/gbproxy/gbproxy_test.c b/openbsc/tests/gbproxy/gbproxy_test.c index 8bf9527..8aef59f 100644 --- a/openbsc/tests/gbproxy/gbproxy_test.c +++ b/openbsc/tests/gbproxy/gbproxy_test.c @@ -811,6 +811,8 @@ static void test_gbproxy_ra_patching() gbcfg.nsip_sgsn_nsei = SGSN_NSEI; gbcfg.core_mcc = 123; gbcfg.core_mnc = 456; + gbcfg.core_apn = talloc_zero_size(NULL, 100); + gbcfg.core_apn_size = gbprox_str_to_apn(gbcfg.core_apn, "foo.bar", 100); sgsn_peer.sin_family = AF_INET; sgsn_peer.sin_port = htons(32000); @@ -862,7 +864,8 @@ static void test_gbproxy_ra_patching() send_ns_unitdata(nsi, NULL, &bss_peer[0], 0x1002, bssgp_act_pdp_ctx_req, sizeof(bssgp_act_pdp_ctx_req)); - /* TODO: Re-configure to test APN IE removal */ + gbcfg.core_apn[0] = 0; + gbcfg.core_apn_size = 0; /* Remove APN */ send_ns_unitdata(nsi, NULL, &bss_peer[0], 0x1002, diff --git a/openbsc/tests/gbproxy/gbproxy_test.ok b/openbsc/tests/gbproxy/gbproxy_test.ok index d3de445..e038afc 100644 --- a/openbsc/tests/gbproxy/gbproxy_test.ok +++ b/openbsc/tests/gbproxy/gbproxy_test.ok @@ -1732,13 +1732,13 @@ PROCESSING UNITDATA from 0x01020304:1111 CALLBACK, event 0, msg length 76, bvci 0x1002 01 ef e2 b7 00 00 00 04 08 88 11 22 33 40 50 60 75 30 00 80 0e 00 35 01 c0 0d 0a 41 05 03 0c 00 00 1f 10 00 00 00 00 00 00 00 00 02 01 21 28 03 02 61 62 27 14 80 80 21 10 01 00 00 10 81 06 00 00 00 00 83 06 00 00 00 00 5a ff 02 -NS UNITDATA MESSAGE to SGSN, BVCI 0x1002, msg length 76 -01 ef e2 b7 00 00 00 04 08 88 21 63 54 40 50 60 75 30 00 80 0e 00 35 01 c0 0d 0a 41 05 03 0c 00 00 1f 10 00 00 00 00 00 00 00 00 02 01 21 28 03 02 61 62 27 14 80 80 21 10 01 00 00 10 81 06 00 00 00 00 83 06 00 00 00 00 5a ff 02 +NS UNITDATA MESSAGE to SGSN, BVCI 0x1002, msg length 81 +01 ef e2 b7 00 00 00 04 08 88 21 63 54 40 50 60 75 30 00 80 0e 00 3a 01 c0 0d 0a 41 05 03 0c 00 00 1f 10 00 00 00 00 00 00 00 00 02 01 21 28 08 03 66 6f 6f 03 62 61 72 27 14 80 80 21 10 01 00 00 10 81 06 00 00 00 00 83 06 00 00 00 00 24 9d 75 -MESSAGE to SGSN at 0x05060708:32000, msg length 80 -00 00 10 02 01 ef e2 b7 00 00 00 04 08 88 21 63 54 40 50 60 75 30 00 80 0e 00 35 01 c0 0d 0a 41 05 03 0c 00 00 1f 10 00 00 00 00 00 00 00 00 02 01 21 28 03 02 61 62 27 14 80 80 21 10 01 00 00 10 81 06 00 00 00 00 83 06 00 00 00 00 5a ff 02 +MESSAGE to SGSN at 0x05060708:32000, msg length 85 +00 00 10 02 01 ef e2 b7 00 00 00 04 08 88 21 63 54 40 50 60 75 30 00 80 0e 00 3a 01 c0 0d 0a 41 05 03 0c 00 00 1f 10 00 00 00 00 00 00 00 00 02 01 21 28 08 03 66 6f 6f 03 62 61 72 27 14 80 80 21 10 01 00 00 10 81 06 00 00 00 00 83 06 00 00 00 00 24 9d 75 -result (UNITDATA) = 80 +result (UNITDATA) = 85 PROCESSING UNITDATA from 0x01020304:1111 00 00 10 02 01 ef e2 b7 00 00 00 04 08 88 11 22 33 40 50 60 75 30 00 80 0e 00 35 01 c0 0d 0a 41 05 03 0c 00 00 1f 10 00 00 00 00 00 00 00 00 02 01 21 28 03 02 61 62 27 14 80 80 21 10 01 00 00 10 81 06 00 00 00 00 83 06 00 00 00 00 5a ff 02 @@ -1746,17 +1746,18 @@ PROCESSING UNITDATA from 0x01020304:1111 CALLBACK, event 0, msg length 76, bvci 0x1002 01 ef e2 b7 00 00 00 04 08 88 11 22 33 40 50 60 75 30 00 80 0e 00 35 01 c0 0d 0a 41 05 03 0c 00 00 1f 10 00 00 00 00 00 00 00 00 02 01 21 28 03 02 61 62 27 14 80 80 21 10 01 00 00 10 81 06 00 00 00 00 83 06 00 00 00 00 5a ff 02 -NS UNITDATA MESSAGE to SGSN, BVCI 0x1002, msg length 76 -01 ef e2 b7 00 00 00 04 08 88 21 63 54 40 50 60 75 30 00 80 0e 00 35 01 c0 0d 0a 41 05 03 0c 00 00 1f 10 00 00 00 00 00 00 00 00 02 01 21 28 03 02 61 62 27 14 80 80 21 10 01 00 00 10 81 06 00 00 00 00 83 06 00 00 00 00 5a ff 02 +NS UNITDATA MESSAGE to SGSN, BVCI 0x1002, msg length 71 +01 ef e2 b7 00 00 00 04 08 88 21 63 54 40 50 60 75 30 00 80 0e 00 30 01 c0 0d 0a 41 05 03 0c 00 00 1f 10 00 00 00 00 00 00 00 00 02 01 21 27 14 80 80 21 10 01 00 00 10 81 06 00 00 00 00 83 06 00 00 00 00 85 fa 60 -MESSAGE to SGSN at 0x05060708:32000, msg length 80 -00 00 10 02 01 ef e2 b7 00 00 00 04 08 88 21 63 54 40 50 60 75 30 00 80 0e 00 35 01 c0 0d 0a 41 05 03 0c 00 00 1f 10 00 00 00 00 00 00 00 00 02 01 21 28 03 02 61 62 27 14 80 80 21 10 01 00 00 10 81 06 00 00 00 00 83 06 00 00 00 00 5a ff 02 +MESSAGE to SGSN at 0x05060708:32000, msg length 75 +00 00 10 02 01 ef e2 b7 00 00 00 04 08 88 21 63 54 40 50 60 75 30 00 80 0e 00 30 01 c0 0d 0a 41 05 03 0c 00 00 1f 10 00 00 00 00 00 00 00 00 02 01 21 27 14 80 80 21 10 01 00 00 10 81 06 00 00 00 00 83 06 00 00 00 00 85 fa 60 -result (UNITDATA) = 80 +result (UNITDATA) = 75 Gbproxy global: RAID patched (BSS ): 8 RAID patched (SGSN): 3 + APN patched : 2 Peers: NSEI 4096, BVCI 4098, not blocked, RAI 112-332-16464-96 --- Bad cases --- @@ -1788,6 +1789,7 @@ Gbproxy global: Invalid Routing Area Identifier : 1 RAID patched (BSS ): 8 RAID patched (SGSN): 4 + APN patched : 2 Peers: NSEI 4096, BVCI 4098, not blocked, RAI 112-332-16464-96 ===== GbProxy test END -- 1.9.1 From jerlbeck at sysmocom.de Thu Jul 3 11:28:17 2014 From: jerlbeck at sysmocom.de (Jacob Erlbeck) Date: Thu, 3 Jul 2014 13:28:17 +0200 Subject: [PATCH 6/6] gprs: Store gbproxy patching state per peer In-Reply-To: <1404386897-27883-1-git-send-email-jerlbeck@sysmocom.de> References: <1404386897-27883-1-git-send-email-jerlbeck@sysmocom.de> Message-ID: <1404386897-27883-6-git-send-email-jerlbeck@sysmocom.de> Currently, all patching state is stored globally in the gbproxy. Thus the feature cannot be used safely with a concentrating gbproxy (NAT). This patch moves the state and relevant counters to the gbprox_peer structure. It adds code to resolve the corresponding peer when packets are received by looking at BVCI, NSEI, and BSSGP IEs (BVCI, RAI/LAI/LAC) when the peer is not passed to the gbprox_patch_bssgp_message() function. Test cases are also added for the SGSN->BSS case including test cases with invalid identifiers. Note that this patch should make it possible to use RAI patching at a NAT gbproxy as long as the messages are not encrypted. Ticket: OW#1185 Sponsored-by: On-Waves ehf --- openbsc/src/gprs/gb_proxy.c | 191 +++++++++++++++++++++++----------- openbsc/tests/gbproxy/gbproxy_test.ok | 20 ++-- 2 files changed, 139 insertions(+), 72 deletions(-) diff --git a/openbsc/src/gprs/gb_proxy.c b/openbsc/src/gprs/gb_proxy.c index ea590b3..bead954 100644 --- a/openbsc/src/gprs/gb_proxy.c +++ b/openbsc/src/gprs/gb_proxy.c @@ -59,11 +59,7 @@ enum gbprox_global_ctr { GBPROX_GLOB_CTR_RESTART_RESET_SGSN, GBPROX_GLOB_CTR_TX_ERR_SGSN, GBPROX_GLOB_CTR_OTHER_ERR, - GBPROX_GLOB_CTR_RAID_PATCHED_BSS, - GBPROX_GLOB_CTR_RAID_PATCHED_SGSN, - GBPROX_GLOB_CTR_APN_PATCHED, - GBPROX_GLOB_CTR_PATCH_CRYPT_ERR, - GBPROX_GLOB_CTR_PATCH_ERR, + GBPROX_GLOB_CTR_PATCH_PEER_ERR, }; static const struct rate_ctr_desc global_ctr_description[] = { @@ -78,11 +74,7 @@ static const struct rate_ctr_desc global_ctr_description[] = { { "restart.sgsn", "Restarted RESET procedure (SGSN)" }, { "tx-err.sgsn", "NS Transmission error (SGSN)" }, { "error", "Other error " }, - { "raid-mod.bss", "RAID patched (BSS )" }, - { "raid-mod.sgsn", "RAID patched (SGSN)" }, - { "apn-mod.sgsn", "APN patched " }, - { "mod-crypt-err", "Patch error: encrypted " }, - { "mod-err", "Patch error: other " }, + { "mod-peer-err", "Patch error: no peer " }, }; static const struct rate_ctr_group_desc global_ctrg_desc = { @@ -109,14 +101,24 @@ enum gbprox_peer_ctr { GBPROX_PEER_CTR_DROPPED, GBPROX_PEER_CTR_INV_NSEI, GBPROX_PEER_CTR_TX_ERR, + GBPROX_PEER_CTR_RAID_PATCHED_BSS, + GBPROX_PEER_CTR_RAID_PATCHED_SGSN, + GBPROX_PEER_CTR_APN_PATCHED, + GBPROX_PEER_CTR_PATCH_CRYPT_ERR, + GBPROX_PEER_CTR_PATCH_ERR, }; static const struct rate_ctr_desc peer_ctr_description[] = { - { "blocked", "BVC Block " }, - { "unblocked", "BVC Unblock " }, - { "dropped", "BVC blocked, dropped packet " }, - { "inv-nsei", "NSEI mismatch " }, - { "tx-err", "NS Transmission error " }, + { "blocked", "BVC Block " }, + { "unblocked", "BVC Unblock " }, + { "dropped", "BVC blocked, dropped packet " }, + { "inv-nsei", "NSEI mismatch " }, + { "tx-err", "NS Transmission error " }, + { "raid-mod.bss", "RAID patched (BSS )" }, + { "raid-mod.sgsn", "RAID patched (SGSN)" }, + { "apn-mod.sgsn", "APN patched " }, + { "mod-crypt-err", "Patch error: encrypted " }, + { "mod-err", "Patch error: other " }, }; static const struct rate_ctr_group_desc peer_ctrg_desc = { @@ -126,10 +128,10 @@ static const struct rate_ctr_group_desc peer_ctrg_desc = { .ctr_desc = peer_ctr_description, }; -static struct gbprox_patch_state { +struct gbprox_patch_state { int local_mnc; int local_mcc; -} gbprox_patch_state = {0}; +}; struct gbprox_peer { struct llist_head list; @@ -146,6 +148,8 @@ struct gbprox_peer { /* Counter */ struct rate_ctr_group *ctrg; + + struct gbprox_patch_state patch_state; }; /* Linked list of all Gb peers (except SGSN) */ @@ -195,6 +199,18 @@ static struct gbprox_peer *peer_by_lai(const uint8_t *la) return NULL; } +/* look-up a peer by its Location Area Code (LAC) */ +static struct gbprox_peer *peer_by_lac(const uint8_t *la) +{ + struct gbprox_peer *peer; + llist_for_each_entry(peer, &gbprox_bts_peers, list) { + if (!memcmp(peer->ra + 3, la + 3, 2)) + return peer; + } + return NULL; +} + + static int check_peer_nsei(struct gbprox_peer *peer, uint16_t nsei) { if (peer->nsei != nsei) { @@ -363,9 +379,10 @@ int gbprox_str_to_apn(uint8_t *apn_enc, const char *str, size_t max_chars) } /* patch RA identifier in place, update peer accordingly */ -static void gbprox_patch_raid(uint8_t *raid_enc, struct gbprox_patch_state *state, +static void gbprox_patch_raid(uint8_t *raid_enc, struct gbprox_peer *peer, int to_bss, const char *log_text) { + struct gbprox_patch_state *state = &peer->patch_state; int old_local_mcc = state->local_mcc; int old_local_mnc = state->local_mnc; int old_mcc; @@ -415,10 +432,10 @@ static void gbprox_patch_raid(uint8_t *raid_enc, struct gbprox_patch_state *stat to_bss ? "BSS" : "SGSN"); if (state->local_mcc || state->local_mnc) { - enum gbprox_global_ctr counter = + enum gbprox_peer_ctr counter = to_bss ? - GBPROX_GLOB_CTR_RAID_PATCHED_SGSN : - GBPROX_GLOB_CTR_RAID_PATCHED_BSS; + GBPROX_PEER_CTR_RAID_PATCHED_SGSN : + GBPROX_PEER_CTR_RAID_PATCHED_BSS; LOGP(DGPRS, LOGL_DEBUG, "Patching %s to %s: " @@ -429,12 +446,13 @@ static void gbprox_patch_raid(uint8_t *raid_enc, struct gbprox_patch_state *stat raid.mcc, raid.mnc, raid.lac, raid.rac); gsm48_construct_ra(raid_enc, &raid); - rate_ctr_inc(&get_global_ctrg()->ctr[counter]); + rate_ctr_inc(&peer->ctrg->ctr[counter]); } } static void gbprox_patch_apn_ie(struct msgb *msg, uint8_t *apn_ie, size_t apn_ie_len, + struct gbprox_peer *peer, size_t *new_apn_ie_len, const char *log_text) { struct apn_ie_hdr { @@ -480,12 +498,12 @@ static void gbprox_patch_apn_ie(struct msgb *msg, hdr->apn_len = gbcfg.core_apn_size; } - rate_ctr_inc(&get_global_ctrg()->ctr[GBPROX_GLOB_CTR_APN_PATCHED]); + rate_ctr_inc(&peer->ctrg->ctr[GBPROX_PEER_CTR_APN_PATCHED]); } static int gbprox_patch_gmm_attach_req(struct msgb *msg, uint8_t *data, size_t data_len, - struct gbprox_patch_state *state, + struct gbprox_peer *peer, int to_bss, int *len_change) { /* Check minimum length, always includes the RAI */ @@ -512,14 +530,14 @@ static int gbprox_patch_gmm_attach_req(struct msgb *msg, data_len -= data[0] + 1; data += data[0] + 1; - gbprox_patch_raid(data, state, to_bss, "LLC/ATTACH_REQ"); + gbprox_patch_raid(data, peer, to_bss, "LLC/ATTACH_REQ"); return 1; } static int gbprox_patch_gmm_attach_ack(struct msgb *msg, uint8_t *data, size_t data_len, - struct gbprox_patch_state *state, + struct gbprox_peer *peer, int to_bss, int *len_change) { /* Check minimum length, always includes the RAI */ @@ -534,14 +552,14 @@ static int gbprox_patch_gmm_attach_ack(struct msgb *msg, data_len -= 3; data += 3; - gbprox_patch_raid(data, state, to_bss, "LLC/ATTACH_ACK"); + gbprox_patch_raid(data, peer, to_bss, "LLC/ATTACH_ACK"); return 1; } static int gbprox_patch_gmm_ra_upd_req(struct msgb *msg, uint8_t *data, size_t data_len, - struct gbprox_patch_state *state, + struct gbprox_peer *peer, int to_bss, int *len_change) { /* Check minimum length, always includes the RAI */ @@ -553,14 +571,14 @@ static int gbprox_patch_gmm_ra_upd_req(struct msgb *msg, data_len -= 1; data += 1; - gbprox_patch_raid(data, state, to_bss, "LLC/RA_UPD_REQ"); + gbprox_patch_raid(data, peer, to_bss, "LLC/RA_UPD_REQ"); return 1; } static int gbprox_patch_gmm_ra_upd_ack(struct msgb *msg, uint8_t *data, size_t data_len, - struct gbprox_patch_state *state, + struct gbprox_peer *peer, int to_bss, int *len_change) { /* Check minimum length, always includes the RAI */ @@ -573,14 +591,14 @@ static int gbprox_patch_gmm_ra_upd_ack(struct msgb *msg, data_len -= 2; data += 2; - gbprox_patch_raid(data, state, to_bss, "LLC/RA_UPD_ACK"); + gbprox_patch_raid(data, peer, to_bss, "LLC/RA_UPD_ACK"); return 1; } static int gbprox_patch_gmm_ptmsi_reall_cmd(struct msgb *msg, uint8_t *data, size_t data_len, - struct gbprox_patch_state *state, + struct gbprox_peer *peer, int to_bss, int *len_change) { /* Check minimum length, always includes the RAI */ @@ -594,14 +612,14 @@ static int gbprox_patch_gmm_ptmsi_reall_cmd(struct msgb *msg, data_len -= 6; data += 6; - gbprox_patch_raid(data, state, to_bss, "LLC/PTMSI_REALL_CMD"); + gbprox_patch_raid(data, peer, to_bss, "LLC/PTMSI_REALL_CMD"); return 1; } static int gbprox_patch_gsm_act_pdp_req(struct msgb *msg, uint8_t *data, size_t data_len, - struct gbprox_patch_state *state, + struct gbprox_peer *peer, int to_bss, int *len_change) { size_t new_len, old_len; @@ -644,7 +662,7 @@ static int gbprox_patch_gsm_act_pdp_req(struct msgb *msg, old_len = data[1] + 2; - gbprox_patch_apn_ie(msg, data, old_len, &new_len, "LLC/ACT_PDP_REQ"); + gbprox_patch_apn_ie(msg, data, old_len, peer, &new_len, "LLC/ACT_PDP_REQ"); *len_change += (int)new_len - (int)old_len; data_len -= old_len; @@ -653,8 +671,31 @@ static int gbprox_patch_gsm_act_pdp_req(struct msgb *msg, return 1; } +struct gbprox_peer *peer_by_bssgp_tlv(struct tlv_parsed *tp) +{ + if (TLVP_PRESENT(tp, BSSGP_IE_BVCI)) { + uint16_t bvci; + + bvci = ntohs(tlvp_val16_unal(tp, BSSGP_IE_BVCI)); + if (bvci >= 2) + return peer_by_bvci(bvci); + } + + if (TLVP_PRESENT(tp, BSSGP_IE_ROUTEING_AREA)) { + uint8_t *rai = (uint8_t *)TLVP_VAL(tp, BSSGP_IE_ROUTEING_AREA); + return peer_by_lac(rai); + } + + if (TLVP_PRESENT(tp, BSSGP_IE_LOCATION_AREA)) { + uint8_t *lai = (uint8_t *)TLVP_VAL(tp, BSSGP_IE_LOCATION_AREA); + return peer_by_lac(lai); + } + + return NULL; +} + static int gbprox_patch_dtap(struct msgb *msg, uint8_t *data, size_t data_len, - struct gbprox_patch_state *state, + struct gbprox_peer *peer, enum gbproxy_patch_mode patch_mode, int to_bss, int *len_change) { @@ -677,31 +718,31 @@ static int gbprox_patch_dtap(struct msgb *msg, uint8_t *data, size_t data_len, switch (g48h->msg_type) { case GSM48_MT_GMM_ATTACH_REQ: return gbprox_patch_gmm_attach_req(msg, data, data_len, - state, to_bss, len_change); + peer, to_bss, len_change); case GSM48_MT_GMM_ATTACH_ACK: if (patch_mode < GBPROX_PATCH_LLC_ATTACH) break; return gbprox_patch_gmm_attach_ack(msg, data, data_len, - state, to_bss, len_change); + peer, to_bss, len_change); case GSM48_MT_GMM_RA_UPD_REQ: if (patch_mode < GBPROX_PATCH_LLC_GMM) break; return gbprox_patch_gmm_ra_upd_req(msg, data, data_len, - state, to_bss, len_change); + peer, to_bss, len_change); case GSM48_MT_GMM_RA_UPD_ACK: if (patch_mode < GBPROX_PATCH_LLC_GMM) break; return gbprox_patch_gmm_ra_upd_ack(msg, data, data_len, - state, to_bss, len_change); + peer, to_bss, len_change); case GSM48_MT_GMM_PTMSI_REALL_CMD: if (patch_mode < GBPROX_PATCH_LLC_GMM) break; return gbprox_patch_gmm_ptmsi_reall_cmd(msg, data, data_len, - state, to_bss, len_change); + peer, to_bss, len_change); case GSM48_MT_GSM_ACT_PDP_REQ: if (patch_mode < GBPROX_PATCH_LLC_GSM) @@ -709,7 +750,7 @@ static int gbprox_patch_dtap(struct msgb *msg, uint8_t *data, size_t data_len, if (gbcfg.core_apn == NULL) break; return gbprox_patch_gsm_act_pdp_req(msg, data, data_len, - state, to_bss, len_change); + peer, to_bss, len_change); default: break; }; @@ -718,7 +759,7 @@ static int gbprox_patch_dtap(struct msgb *msg, uint8_t *data, size_t data_len, } static void gbprox_patch_llc(struct msgb *msg, uint8_t *llc, size_t llc_len, - struct gbprox_patch_state *state, + struct gbprox_peer *peer, enum gbproxy_patch_mode patch_mode, int to_bss) { struct gprs_llc_hdr_parsed ghp = {0}; @@ -755,7 +796,7 @@ static void gbprox_patch_llc(struct msgb *msg, uint8_t *llc, size_t llc_len, if (gbcfg.patch_mode > GBPROX_PATCH_LLC_ATTACH_REQ) { /* LLC patch (GMM) has been requested explicitely */ err_info = "GMM message is encrypted"; - err_ctr = GBPROX_GLOB_CTR_PATCH_CRYPT_ERR; + err_ctr = GBPROX_PEER_CTR_PATCH_CRYPT_ERR; goto patch_error; } @@ -766,7 +807,7 @@ static void gbprox_patch_llc(struct msgb *msg, uint8_t *llc, size_t llc_len, data = ghp.data; data_len = ghp.data_len; - rc = gbprox_patch_dtap(msg, data, data_len, state, patch_mode, to_bss, + rc = gbprox_patch_dtap(msg, data, data_len, peer, patch_mode, to_bss, &len_change); if (rc > 0) { @@ -778,7 +819,7 @@ static void gbprox_patch_llc(struct msgb *msg, uint8_t *llc, size_t llc_len, /* most probably a one byte length */ if (llc_len > 127) { err_info = "Cannot increase size"; - err_ctr = GBPROX_GLOB_CTR_PATCH_ERR; + err_ctr = GBPROX_PEER_CTR_PATCH_ERR; goto patch_error; } llc[-1] = llc_len | 0x80; @@ -801,7 +842,7 @@ static void gbprox_patch_llc(struct msgb *msg, uint8_t *llc, size_t llc_len, patch_error: OSMO_ASSERT(err_ctr >= 0); - rate_ctr_inc(&get_global_ctrg()->ctr[err_ctr]); + rate_ctr_inc(&peer->ctrg->ctr[err_ctr]); LOGP(DGPRS, LOGL_ERROR, "Failed to patch BSSGP/GMM message as requested: %s.\n", err_info); @@ -809,13 +850,14 @@ patch_error: } /* patch BSSGP message to use core_mcc/mnc on the SGSN side */ -static void gbprox_patch_bssgp_message(struct msgb *msg, int to_bss) +static void gbprox_patch_bssgp_message(struct msgb *msg, + struct gbprox_peer *peer, int to_bss) { struct bssgp_normal_hdr *bgph; struct bssgp_ud_hdr *budh; struct tlv_parsed tp; uint8_t pdu_type; - struct gbprox_patch_state *state = &gbprox_patch_state; + struct gbprox_patch_state *state = NULL; uint8_t *data; size_t data_len; enum gbproxy_patch_mode patch_mode; @@ -830,9 +872,6 @@ static void gbprox_patch_bssgp_message(struct msgb *msg, int to_bss) if (patch_mode == GBPROX_PATCH_DEFAULT) patch_mode = GBPROX_PATCH_LLC; - if (to_bss && !state->local_mcc && !state->local_mnc) - return; - if (pdu_type == BSSGP_PDUT_UL_UNITDATA || pdu_type == BSSGP_PDUT_DL_UNITDATA) { data = budh->data; @@ -845,32 +884,60 @@ static void gbprox_patch_bssgp_message(struct msgb *msg, int to_bss) /* fix BSSGP */ bssgp_tlv_parse(&tp, data, data_len); - if (TLVP_PRESENT(&tp, BSSGP_IE_ROUTEING_AREA)) + if (!peer && msgb_bvci(msg) >= 2) + peer = peer_by_bvci(msgb_bvci(msg)); + + if (!peer && !to_bss) + peer = peer_by_nsei(msgb_nsei(msg)); + + if (!peer) + peer = peer_by_bssgp_tlv(&tp); + + if (!peer) { + LOGP(DLLC, LOGL_INFO, + "NSEI=%d(%s) patching: didn't find peer for message, " + "PDU %d\n", + msgb_nsei(msg), to_bss ? "SGSN" : "BSS", pdu_type); + /* Increment counter */ + rate_ctr_inc(&get_global_ctrg()->ctr[GBPROX_GLOB_CTR_PATCH_PEER_ERR]); + return; + } + + state = &peer->patch_state; + + if (to_bss && !state->local_mcc && !state->local_mnc) + return; + + if (TLVP_PRESENT(&tp, BSSGP_IE_ROUTEING_AREA)) { gbprox_patch_raid((uint8_t *)TLVP_VAL(&tp, BSSGP_IE_ROUTEING_AREA), - state, to_bss, "ROUTING_AREA"); + peer, to_bss, "ROUTING_AREA"); + } if (TLVP_PRESENT(&tp, BSSGP_IE_CELL_ID)) gbprox_patch_raid((uint8_t *)TLVP_VAL(&tp, BSSGP_IE_CELL_ID), - state, to_bss, "CELL_ID"); + peer, to_bss, "CELL_ID"); if (TLVP_PRESENT(&tp, BSSGP_IE_LLC_PDU) && patch_mode >= GBPROX_PATCH_LLC_ATTACH_REQ) { uint8_t *llc = (uint8_t *)TLVP_VAL(&tp, BSSGP_IE_LLC_PDU); size_t llc_len = TLVP_LEN(&tp, BSSGP_IE_LLC_PDU); - gbprox_patch_llc(msg, llc, llc_len, state, patch_mode, to_bss); + gbprox_patch_llc(msg, llc, llc_len, peer, patch_mode, to_bss); /* Note that the tp struct might contain invalid pointers here * if the LLC field has changed its size */ } } /* feed a message down the NS-VC associated with the specified peer */ -static int gbprox_relay2sgsn(struct msgb *old_msg, uint16_t ns_bvci) +static int gbprox_relay2sgsn(struct msgb *old_msg, + struct gbprox_peer *peer, uint16_t ns_bvci) { /* create a copy of the message so the old one can * be free()d safely when we return from gbprox_rcvmsg() */ struct msgb *msg = msgb_copy(old_msg, "msgb_relay2sgsn"); int rc; + gbprox_patch_bssgp_message(msg, peer, 0); + DEBUGP(DGPRS, "NSEI=%u proxying BTS->SGSN (NS_BVCI=%u, NSEI=%u)\n", msgb_nsei(msg), ns_bvci, gbcfg.nsip_sgsn_nsei); @@ -879,8 +946,6 @@ static int gbprox_relay2sgsn(struct msgb *old_msg, uint16_t ns_bvci) strip_ns_hdr(msg); - gbprox_patch_bssgp_message(msg, 0); - rc = gprs_ns_sendmsg(bssgp_nsi, msg); if (rc < 0) rate_ctr_inc(&get_global_ctrg()->ctr[GBPROX_GLOB_CTR_TX_ERR_SGSN]); @@ -971,7 +1036,7 @@ static int gbprox_rx_sig_from_bss(struct msgb *msg, uint16_t nsei, struct tlv_parsed tp; uint8_t pdu_type = bgph->pdu_type; int data_len = msgb_bssgp_len(msg) - sizeof(*bgph); - struct gbprox_peer *from_peer; + struct gbprox_peer *from_peer = NULL; struct gprs_ra_id raid; if (ns_bvci != 0 && ns_bvci != 1) { @@ -1062,7 +1127,7 @@ static int gbprox_rx_sig_from_bss(struct msgb *msg, uint16_t nsei, /* Normally, we can simply pass on all signalling messages from BSS to * SGSN */ - return gbprox_relay2sgsn(msg, ns_bvci); + return gbprox_relay2sgsn(msg, from_peer, ns_bvci); err_no_peer: LOGP(DGPRS, LOGL_ERROR, "NSEI=%u(BSS) cannot find peer based on NSEI\n", nsei); @@ -1285,7 +1350,7 @@ int gbprox_rcvmsg(struct msgb *msg, uint16_t nsei, uint16_t ns_bvci, uint16_t ns int remote_end_is_sgsn = nsei == gbcfg.nsip_sgsn_nsei; if (remote_end_is_sgsn) - gbprox_patch_bssgp_message(msg, 1); + gbprox_patch_bssgp_message(msg, NULL, 1); /* Only BVCI=0 messages need special treatment */ if (ns_bvci == 0 || ns_bvci == 1) { @@ -1300,7 +1365,7 @@ int gbprox_rcvmsg(struct msgb *msg, uint16_t nsei, uint16_t ns_bvci, uint16_t ns if (!remote_end_is_sgsn) { if (peer) check_peer_nsei(peer, nsei); - return gbprox_relay2sgsn(msg, ns_bvci); + return gbprox_relay2sgsn(msg, peer, ns_bvci); } /* else: SGSN -> BSS direction */ diff --git a/openbsc/tests/gbproxy/gbproxy_test.ok b/openbsc/tests/gbproxy/gbproxy_test.ok index e038afc..40b5376 100644 --- a/openbsc/tests/gbproxy/gbproxy_test.ok +++ b/openbsc/tests/gbproxy/gbproxy_test.ok @@ -1621,6 +1621,7 @@ Current NS-VCIs: Peers: NSEI 4096, BVCI 4098, not blocked, RAI 112-332-16464-96 + RAID patched (BSS ): 1 PROCESSING BVC_RESET_ACK from 0x05060708:32000 00 00 00 00 23 04 82 10 02 @@ -1664,10 +1665,10 @@ MESSAGE to BSS at 0x01020304:1111, msg length 22 result (BVC_SUSPEND_ACK) = 22 Gbproxy global: - RAID patched (BSS ): 2 - RAID patched (SGSN): 1 Peers: NSEI 4096, BVCI 4098, not blocked, RAI 112-332-16464-96 + RAID patched (BSS ): 2 + RAID patched (SGSN): 1 --- Send message from BSS 1 to SGSN, BVCI 0x1002 --- PROCESSING UNITDATA from 0x01020304:1111 @@ -1755,11 +1756,11 @@ MESSAGE to SGSN at 0x05060708:32000, msg length 75 result (UNITDATA) = 75 Gbproxy global: +Peers: + NSEI 4096, BVCI 4098, not blocked, RAI 112-332-16464-96 RAID patched (BSS ): 8 RAID patched (SGSN): 3 APN patched : 2 -Peers: - NSEI 4096, BVCI 4098, not blocked, RAI 112-332-16464-96 --- Bad cases --- PROCESSING BVC_RESET_ACK from 0x05060708:32000 @@ -1777,20 +1778,21 @@ CALLBACK, event 0, msg length 18, bvci 0x0000 0c 1f 84 cc d1 75 8b 1b 86 00 f1 99 00 63 60 1d 81 01 NS UNITDATA MESSAGE to SGSN, BVCI 0x0000, msg length 24 -41 07 81 05 15 92 0c 1f 84 cc d1 75 8b 1b 86 11 22 33 00 63 60 1d 81 01 +41 07 81 05 15 92 0c 1f 84 cc d1 75 8b 1b 86 00 f1 99 00 63 60 1d 81 01 MESSAGE to SGSN at 0x05060708:32000, msg length 28 -00 00 00 00 41 07 81 05 15 92 0c 1f 84 cc d1 75 8b 1b 86 11 22 33 00 63 60 1d 81 01 +00 00 00 00 41 07 81 05 15 92 0c 1f 84 cc d1 75 8b 1b 86 00 f1 99 00 63 60 1d 81 01 result (BVC_SUSPEND_ACK) = 28 Gbproxy global: Invalid BVC Identifier : 1 Invalid Routing Area Identifier : 1 - RAID patched (BSS ): 8 - RAID patched (SGSN): 4 - APN patched : 2 + Patch error: no peer : 2 Peers: NSEI 4096, BVCI 4098, not blocked, RAI 112-332-16464-96 + RAID patched (BSS ): 8 + RAID patched (SGSN): 3 + APN patched : 2 ===== GbProxy test END -- 1.9.1 From holger at freyther.de Fri Jul 4 06:46:45 2014 From: holger at freyther.de (Holger Hans Peter Freyther) Date: Fri, 4 Jul 2014 08:46:45 +0200 Subject: [PATCH 1/6] gprs/test: Add additional gbproxy tests In-Reply-To: <1404386897-27883-1-git-send-email-jerlbeck@sysmocom.de> References: <1404386897-27883-1-git-send-email-jerlbeck@sysmocom.de> Message-ID: <20140704064645.GB4402@xiaoyu.lan> On Thu, Jul 03, 2014 at 01:28:12PM +0200, Jacob Erlbeck wrote: > +static void send_bssgp_suspend(struct gprs_ns_inst *nsi, > + struct gprs_ra_id *raid) > +{ > + if (raid) Every branch spawns a new dimension in your test matrix. It is increasing complexity. All your callers pass a non-NULL raid. The best way is to no check for it being null then. > + struct gprs_ns_inst *nsi = gprs_ns_instantiate(gprs_ns_callback, NULL); > + struct sockaddr_in bss_peer[1] = {{0},}; > + struct sockaddr_in sgsn_peer= {0}; > + struct gprs_ra_id rai_bss = > + {.mcc = 112, .mnc = 332, .lac = 16464, .rac = 96}; > + struct gprs_ra_id rai_sgsn = > + {.mcc = 123, .mnc = 456, .lac = 16464, .rac = 96}; > + struct gprs_ra_id rai_unknown = > + {.mcc = 1, .mnc = 99, .lac = 99, .rac = 96}; > + > + bssgp_nsi = nsi; > + gbcfg.nsi = bssgp_nsi; > + gbcfg.nsip_sgsn_nsei = SGSN_NSEI; > + > + sgsn_peer.sin_family = AF_INET; > + sgsn_peer.sin_port = htons(32000); > + sgsn_peer.sin_addr.s_addr = htonl(REMOTE_SGSN_ADDR); > + > + bss_peer[0].sin_family = AF_INET; > + bss_peer[0].sin_port = htons(1111); > + bss_peer[0].sin_addr.s_addr = htonl(REMOTE_BSS_ADDR); > + > + printf("--- Initialise SGSN ---\n\n"); > + > + gprs_ns_nsip_connect(nsi, &sgsn_peer, SGSN_NSEI, SGSN_NSEI+1); > + send_ns_reset_ack(nsi, &sgsn_peer, SGSN_NSEI+1, SGSN_NSEI); > + send_ns_alive_ack(nsi, &sgsn_peer); > + send_ns_unblock_ack(nsi, &sgsn_peer); > + send_ns_alive(nsi, &sgsn_peer); > + gprs_dump_nsi(nsi); this can be easily shared. You seem to only vary the amount of bss_peer's you create. > + gbprox_dump_peers(stdout, 0, 1); Please have a look here: http://qt-project.org/wiki/API_Design_Principles specially read about the boolean parameter trap. My train just arrived. I will continue the review in a bit. have a nice day holger From jerlbeck at sysmocom.de Mon Jul 7 08:45:59 2014 From: jerlbeck at sysmocom.de (Jacob Erlbeck) Date: Mon, 7 Jul 2014 10:45:59 +0200 Subject: [PATCH 1/3] gprs/test: Remove verbose parameter of gbprox_dump_* functions In-Reply-To: <1404386897-27883-1-git-send-email-jerlbeck@sysmocom.de> References: <1404386897-27883-1-git-send-email-jerlbeck@sysmocom.de> Message-ID: <1404722761-25939-1-git-send-email-jerlbeck@sysmocom.de> This parameter is not used (the methods are always called with an argument of 1 in the third position). Thus the parameter is removed completely. Sponsored-by: On-Waves ehf --- openbsc/include/openbsc/gb_proxy.h | 4 +-- openbsc/src/gprs/gb_proxy.c | 10 ++----- openbsc/tests/gbproxy/gbproxy_test.c | 52 ++++++++++++++++++------------------ 3 files changed, 30 insertions(+), 36 deletions(-) diff --git a/openbsc/include/openbsc/gb_proxy.h b/openbsc/include/openbsc/gb_proxy.h index 4d189a6..5f1f3a7 100644 --- a/openbsc/include/openbsc/gb_proxy.h +++ b/openbsc/include/openbsc/gb_proxy.h @@ -37,7 +37,7 @@ int gbprox_signal(unsigned int subsys, unsigned int signal, /* Reset all persistent NS-VC's */ int gbprox_reset_persistent_nsvcs(struct gprs_ns_inst *nsi); -int gbprox_dump_global(FILE *stream, int indent, int verbose); -int gbprox_dump_peers(FILE *stream, int indent, int verbose); +int gbprox_dump_global(FILE *stream, int indent); +int gbprox_dump_peers(FILE *stream, int indent); void gbprox_reset(); #endif diff --git a/openbsc/src/gprs/gb_proxy.c b/openbsc/src/gprs/gb_proxy.c index 4799344..9de2ca9 100644 --- a/openbsc/src/gprs/gb_proxy.c +++ b/openbsc/src/gprs/gb_proxy.c @@ -806,7 +806,7 @@ int gbprox_signal(unsigned int subsys, unsigned int signal, return 0; } -int gbprox_dump_global(FILE *stream, int indent, int verbose) +int gbprox_dump_global(FILE *stream, int indent) { unsigned int i; const struct rate_ctr_group_desc *desc; @@ -816,9 +816,6 @@ int gbprox_dump_global(FILE *stream, int indent, int verbose) if (rc < 0) return rc; - if (!verbose) - return 0; - desc = get_global_ctrg()->desc; for (i = 0; i < desc->num_ctr; i++) { @@ -837,7 +834,7 @@ int gbprox_dump_global(FILE *stream, int indent, int verbose) return 0; } -int gbprox_dump_peers(FILE *stream, int indent, int verbose) +int gbprox_dump_peers(FILE *stream, int indent) { struct gbprox_peer *peer; struct gprs_ra_id raid; @@ -862,9 +859,6 @@ int gbprox_dump_peers(FILE *stream, int indent, int verbose) if (rc < 0) return rc; - if (!verbose) - continue; - desc = peer->ctrg->desc; for (i = 0; i < desc->num_ctr; i++) { diff --git a/openbsc/tests/gbproxy/gbproxy_test.c b/openbsc/tests/gbproxy/gbproxy_test.c index ea07a77..a8f4eaf 100644 --- a/openbsc/tests/gbproxy/gbproxy_test.c +++ b/openbsc/tests/gbproxy/gbproxy_test.c @@ -420,7 +420,7 @@ static void test_gbproxy() setup_ns(nsi, &bss_peer[0], 0x1001, 0x1000); setup_bssgp(nsi, &bss_peer[0], 0x1002); gprs_dump_nsi(nsi); - gbprox_dump_peers(stdout, 0, 1); + gbprox_dump_peers(stdout, 0); send_bssgp_reset_ack(nsi, &sgsn_peer, 0x1002); @@ -429,7 +429,7 @@ static void test_gbproxy() setup_ns(nsi, &bss_peer[1], 0x2001, 0x2000); setup_bssgp(nsi, &bss_peer[1], 0x2002); gprs_dump_nsi(nsi); - gbprox_dump_peers(stdout, 0, 1); + gbprox_dump_peers(stdout, 0); send_bssgp_reset_ack(nsi, &sgsn_peer, 0x2002); @@ -437,43 +437,43 @@ static void test_gbproxy() setup_ns(nsi, &bss_peer[2], 0x1001, 0x1000); gprs_dump_nsi(nsi); - gbprox_dump_peers(stdout, 0, 1); + gbprox_dump_peers(stdout, 0); printf("--- Move BSS 2 to former BSS 1 port ---\n\n"); setup_ns(nsi, &bss_peer[0], 0x2001, 0x2000); gprs_dump_nsi(nsi); - gbprox_dump_peers(stdout, 0, 1); + gbprox_dump_peers(stdout, 0); printf("--- Move BSS 1 to current BSS 2 port ---\n\n"); setup_ns(nsi, &bss_peer[0], 0x2001, 0x2000); gprs_dump_nsi(nsi); - gbprox_dump_peers(stdout, 0, 1); + gbprox_dump_peers(stdout, 0); printf("--- Move BSS 2 to new port ---\n\n"); setup_ns(nsi, &bss_peer[3], 0x2001, 0x2000); gprs_dump_nsi(nsi); - gbprox_dump_peers(stdout, 0, 1); + gbprox_dump_peers(stdout, 0); printf("--- Move BSS 2 to former BSS 1 port ---\n\n"); setup_ns(nsi, &bss_peer[2], 0x2001, 0x2000); gprs_dump_nsi(nsi); - gbprox_dump_peers(stdout, 0, 1); + gbprox_dump_peers(stdout, 0); printf("--- Move BSS 1 to original BSS 1 port ---\n\n"); setup_ns(nsi, &bss_peer[0], 0x1001, 0x1000); gprs_dump_nsi(nsi); - gbprox_dump_peers(stdout, 0, 1); + gbprox_dump_peers(stdout, 0); printf("--- Reset BSS 1 with a new BVCI ---\n\n"); setup_bssgp(nsi, &bss_peer[0], 0x1012); gprs_dump_nsi(nsi); - gbprox_dump_peers(stdout, 0, 1); + gbprox_dump_peers(stdout, 0); send_bssgp_reset_ack(nsi, &sgsn_peer, 0x1012); @@ -481,7 +481,7 @@ static void test_gbproxy() setup_bssgp(nsi, &bss_peer[0], 0x1002); gprs_dump_nsi(nsi); - gbprox_dump_peers(stdout, 0, 1); + gbprox_dump_peers(stdout, 0); send_bssgp_reset_ack(nsi, &sgsn_peer, 0x1002); @@ -489,7 +489,7 @@ static void test_gbproxy() setup_bssgp(nsi, &bss_peer[0], 0x1002); gprs_dump_nsi(nsi); - gbprox_dump_peers(stdout, 0, 1); + gbprox_dump_peers(stdout, 0); send_bssgp_reset_ack(nsi, &sgsn_peer, 0x1002); @@ -521,9 +521,9 @@ static void test_gbproxy() setup_bssgp(nsi, &bss_peer[2], 0x1002); gprs_dump_nsi(nsi); - gbprox_dump_peers(stdout, 0, 1); + gbprox_dump_peers(stdout, 0); - gbprox_dump_global(stdout, 0, 1); + gbprox_dump_global(stdout, 0); send_bssgp_reset_ack(nsi, &sgsn_peer, 0x1002); @@ -539,7 +539,7 @@ static void test_gbproxy() send_ns_unitdata(nsi, NULL, &sgsn_peer, 0x10ff, (uint8_t *)"", 0); - gbprox_dump_global(stdout, 0, 1); + gbprox_dump_global(stdout, 0); gprs_ns_destroy(nsi); nsi = NULL; @@ -585,13 +585,13 @@ static void test_gbproxy_ident_changes() setup_bssgp(nsi, &bss_peer[0], bvci[0]); send_bssgp_reset_ack(nsi, &sgsn_peer, bvci[0]); - gbprox_dump_peers(stdout, 0, 1); + gbprox_dump_peers(stdout, 0); printf("--- Setup BVCI 2 ---\n\n"); setup_bssgp(nsi, &bss_peer[0], bvci[1]); send_bssgp_reset_ack(nsi, &sgsn_peer, bvci[1]); - gbprox_dump_peers(stdout, 0, 1); + gbprox_dump_peers(stdout, 0); printf("--- Send message from BSS 1 to SGSN and back, BVCI 1 ---\n\n"); @@ -612,13 +612,13 @@ static void test_gbproxy_ident_changes() setup_bssgp(nsi, &bss_peer[0], bvci[0]); send_bssgp_reset_ack(nsi, &sgsn_peer, bvci[0]); - gbprox_dump_peers(stdout, 0, 1); + gbprox_dump_peers(stdout, 0); printf("--- Setup BVCI 3 ---\n\n"); setup_bssgp(nsi, &bss_peer[0], bvci[2]); send_bssgp_reset_ack(nsi, &sgsn_peer, bvci[2]); - gbprox_dump_peers(stdout, 0, 1); + gbprox_dump_peers(stdout, 0); printf("--- Send message from BSS 1 to SGSN and back, BVCI 1 ---\n\n"); @@ -629,9 +629,9 @@ static void test_gbproxy_ident_changes() " (should fail) ---\n\n"); send_ns_unitdata(nsi, NULL, &bss_peer[0], bvci[1], (uint8_t *)"", 0); - gbprox_dump_peers(stdout, 0, 1); + gbprox_dump_peers(stdout, 0); send_ns_unitdata(nsi, NULL, &sgsn_peer, bvci[1], (uint8_t *)"", 0); - gbprox_dump_peers(stdout, 0, 1); + gbprox_dump_peers(stdout, 0); printf("--- Send message from BSS 1 to SGSN and back, BVCI 3 ---\n\n"); @@ -647,13 +647,13 @@ static void test_gbproxy_ident_changes() setup_bssgp(nsi, &bss_peer[0], bvci[0]); send_bssgp_reset_ack(nsi, &sgsn_peer, bvci[0]); - gbprox_dump_peers(stdout, 0, 1); + gbprox_dump_peers(stdout, 0); printf("--- Setup BVCI 4 ---\n\n"); setup_bssgp(nsi, &bss_peer[0], bvci[3]); send_bssgp_reset_ack(nsi, &sgsn_peer, bvci[3]); - gbprox_dump_peers(stdout, 0, 1); + gbprox_dump_peers(stdout, 0); printf("--- Send message from BSS 1 to SGSN and back, BVCI 1 ---\n\n"); @@ -664,9 +664,9 @@ static void test_gbproxy_ident_changes() " (should fail) ---\n\n"); send_ns_unitdata(nsi, NULL, &bss_peer[0], bvci[1], (uint8_t *)"", 0); - gbprox_dump_peers(stdout, 0, 1); + gbprox_dump_peers(stdout, 0); send_ns_unitdata(nsi, NULL, &sgsn_peer, bvci[1], (uint8_t *)"", 0); - gbprox_dump_peers(stdout, 0, 1); + gbprox_dump_peers(stdout, 0); printf("--- Send message from BSS 1 to SGSN and back, BVCI 3 ---\n\n"); @@ -678,8 +678,8 @@ static void test_gbproxy_ident_changes() send_ns_unitdata(nsi, NULL, &bss_peer[0], bvci[3], (uint8_t *)"", 0); send_ns_unitdata(nsi, NULL, &sgsn_peer, bvci[3], (uint8_t *)"", 0); - gbprox_dump_global(stdout, 0, 1); - gbprox_dump_peers(stdout, 0, 1); + gbprox_dump_global(stdout, 0); + gbprox_dump_peers(stdout, 0); gprs_ns_destroy(nsi); nsi = NULL; -- 1.9.1 From jerlbeck at sysmocom.de Mon Jul 7 08:46:00 2014 From: jerlbeck at sysmocom.de (Jacob Erlbeck) Date: Mon, 7 Jul 2014 10:46:00 +0200 Subject: [PATCH 2/3] gprs/test: Add connect_sgsn() function In-Reply-To: <1404722761-25939-1-git-send-email-jerlbeck@sysmocom.de> References: <1404386897-27883-1-git-send-email-jerlbeck@sysmocom.de> <1404722761-25939-1-git-send-email-jerlbeck@sysmocom.de> Message-ID: <1404722761-25939-2-git-send-email-jerlbeck@sysmocom.de> This function abstracts identical code sequences that are used at multiple places. Sponsored-by: On-Waves ehf --- openbsc/tests/gbproxy/gbproxy_test.c | 21 +++++++++++---------- 1 file changed, 11 insertions(+), 10 deletions(-) diff --git a/openbsc/tests/gbproxy/gbproxy_test.c b/openbsc/tests/gbproxy/gbproxy_test.c index a8f4eaf..ba1c51b 100644 --- a/openbsc/tests/gbproxy/gbproxy_test.c +++ b/openbsc/tests/gbproxy/gbproxy_test.c @@ -193,6 +193,15 @@ static void setup_bssgp(struct gprs_ns_inst *nsi, struct sockaddr_in *src_addr, send_bssgp_reset(nsi, src_addr, bvci); } +static void connect_sgsn(struct gprs_ns_inst *nsi, struct sockaddr_in *sgsn_peer) +{ + gprs_ns_nsip_connect(nsi, sgsn_peer, SGSN_NSEI, SGSN_NSEI+1); + send_ns_reset_ack(nsi, sgsn_peer, SGSN_NSEI+1, SGSN_NSEI); + send_ns_alive_ack(nsi, sgsn_peer); + send_ns_unblock_ack(nsi, sgsn_peer); + send_ns_alive(nsi, sgsn_peer); +} + int gprs_ns_rcvmsg(struct gprs_ns_inst *nsi, struct msgb *msg, struct sockaddr_in *saddr, enum gprs_ns_ll ll); @@ -408,11 +417,7 @@ static void test_gbproxy() printf("--- Initialise SGSN ---\n\n"); - gprs_ns_nsip_connect(nsi, &sgsn_peer, SGSN_NSEI, SGSN_NSEI+1); - send_ns_reset_ack(nsi, &sgsn_peer, SGSN_NSEI+1, SGSN_NSEI); - send_ns_alive_ack(nsi, &sgsn_peer); - send_ns_unblock_ack(nsi, &sgsn_peer); - send_ns_alive(nsi, &sgsn_peer); + connect_sgsn(nsi, &sgsn_peer); gprs_dump_nsi(nsi); printf("--- Initialise BSS 1 ---\n\n"); @@ -569,11 +574,7 @@ static void test_gbproxy_ident_changes() printf("--- Initialise SGSN ---\n\n"); - gprs_ns_nsip_connect(nsi, &sgsn_peer, SGSN_NSEI, SGSN_NSEI+1); - send_ns_reset_ack(nsi, &sgsn_peer, SGSN_NSEI+1, SGSN_NSEI); - send_ns_alive_ack(nsi, &sgsn_peer); - send_ns_unblock_ack(nsi, &sgsn_peer); - send_ns_alive(nsi, &sgsn_peer); + connect_sgsn(nsi, &sgsn_peer); gprs_dump_nsi(nsi); printf("--- Initialise BSS 1 ---\n\n"); -- 1.9.1 From jerlbeck at sysmocom.de Mon Jul 7 08:46:01 2014 From: jerlbeck at sysmocom.de (Jacob Erlbeck) Date: Mon, 7 Jul 2014 10:46:01 +0200 Subject: [PATCH 3/3] gprs/test: Add additional gbproxy tests In-Reply-To: <1404722761-25939-1-git-send-email-jerlbeck@sysmocom.de> References: <1404386897-27883-1-git-send-email-jerlbeck@sysmocom.de> <1404722761-25939-1-git-send-email-jerlbeck@sysmocom.de> Message-ID: <1404722761-25939-3-git-send-email-jerlbeck@sysmocom.de> This adds a test case with several messages to test BSSGP patching. New messages: - BSSGP/DTAP Attach Request - BSSGP/DTAP Attach Accept - BSSGP/DTAP Routing Area Update Request - BSSGP/DTAP Routing Area Update Accept - BSSGP/DTAP Activate PDP Context Request - BSSGP SUSPEND - BSSGP SUSPEND ACK Sponsored-by: On-Waves ehf --- openbsc/tests/gbproxy/gbproxy_test.c | 193 +++++++++++++++++++++++- openbsc/tests/gbproxy/gbproxy_test.ok | 268 ++++++++++++++++++++++++++++++++++ 2 files changed, 460 insertions(+), 1 deletion(-) diff --git a/openbsc/tests/gbproxy/gbproxy_test.c b/openbsc/tests/gbproxy/gbproxy_test.c index ba1c51b..97dbfec 100644 --- a/openbsc/tests/gbproxy/gbproxy_test.c +++ b/openbsc/tests/gbproxy/gbproxy_test.c @@ -28,13 +28,88 @@ #include #include +#include #define REMOTE_BSS_ADDR 0x01020304 #define REMOTE_SGSN_ADDR 0x05060708 #define SGSN_NSEI 0x0100 -struct gbproxy_config gbcfg; +struct gbproxy_config gbcfg = {0}; + +/* Base Station Subsystem GPRS Protocol: GSM A-I/F DTAP - Attach Request */ +static const unsigned char bssgp_attach_req[75] = { + 0x01, 0xbb, 0xc5, 0x46, 0x79, 0x00, 0x00, 0x04, + 0x08, 0x88, 0x11, 0x22, 0x33, 0x40, 0x50, 0x60, + 0x75, 0x30, 0x00, 0x80, 0x0e, 0x00, 0x34, 0x01, + 0xc0, 0x01, 0x08, 0x01, 0x02, 0xf5, 0xe0, 0x21, + 0x08, 0x02, 0x05, 0xf4, 0xfb, 0xc5, 0x46, 0x79, + 0x11, 0x22, 0x33, 0x40, 0x50, 0x60, 0x19, 0x18, + 0xb3, 0x43, 0x2b, 0x25, 0x96, 0x62, 0x00, 0x60, + 0x80, 0x9a, 0xc2, 0xc6, 0x62, 0x00, 0x60, 0x80, + 0xba, 0xc8, 0xc6, 0x62, 0x00, 0x60, 0x80, 0x00, + 0x16, 0x6d, 0x01 +}; + +/* Base Station Subsystem GPRS Protocol: GSM A-I/F DTAP - Attach Accept */ +static const unsigned char bssgp_attach_acc[88] = { + 0x00, 0xbb, 0xc5, 0x46, 0x79, 0x00, 0x50, 0x20, + 0x16, 0x82, 0x02, 0x58, 0x13, 0x99, 0x18, 0xb3, + 0x43, 0x2b, 0x25, 0x96, 0x62, 0x00, 0x60, 0x80, + 0x9a, 0xc2, 0xc6, 0x62, 0x00, 0x60, 0x80, 0xba, + 0xc8, 0xc6, 0x62, 0x00, 0x60, 0x80, 0x00, 0x0a, + 0x82, 0x08, 0x02, 0x0d, 0x88, 0x11, 0x12, 0x13, + 0x14, 0x15, 0x16, 0x17, 0x18, 0x00, 0x81, 0x00, + 0x0e, 0x9e, 0x41, 0xc0, 0x05, 0x08, 0x02, 0x01, + 0x49, 0x04, 0x21, 0x63, 0x54, 0x40, 0x50, 0x60, + 0x19, 0xcd, 0xd7, 0x08, 0x17, 0x16, 0x18, 0x05, + 0xf4, 0xfb, 0xc5, 0x47, 0x22, 0x42, 0x67, 0x9a +}; + +/* Base Station Subsystem GPRS Protocol: GSM A-I/F DTAP - Routing Area Update Request */ +static const unsigned char bssgp_ra_upd_req[85] = { + 0x01, 0xaf, 0xe2, 0x80, 0x6e, 0x00, 0x00, 0x04, + 0x08, 0x88, 0x11, 0x22, 0x33, 0x40, 0x50, 0x60, + 0x70, 0x80, 0x00, 0x80, 0x0e, 0x00, 0x3e, 0x01, + 0xc0, 0x15, 0x08, 0x08, 0x10, 0x11, 0x22, 0x33, + 0x40, 0x50, 0x60, 0x1d, 0x19, 0x13, 0x42, 0x33, + 0x57, 0x2b, 0xf7, 0xc8, 0x48, 0x02, 0x13, 0x48, + 0x50, 0xc8, 0x48, 0x02, 0x14, 0x48, 0x50, 0xc8, + 0x48, 0x02, 0x17, 0x49, 0x10, 0xc8, 0x48, 0x02, + 0x00, 0x19, 0x8b, 0xb2, 0x92, 0x17, 0x16, 0x27, + 0x07, 0x04, 0x31, 0x02, 0xe5, 0xe0, 0x32, 0x02, + 0x20, 0x00, 0x96, 0x3e, 0x97 +}; + +/* Base Station Subsystem GPRS Protocol: GSM A-I/F DTAP - Routing Area Update Accept */ +static const unsigned char bssgp_ra_upd_acc[91] = { + 0x00, 0xaf, 0xe2, 0x80, 0x6e, 0x00, 0x50, 0x20, + 0x16, 0x82, 0x02, 0x58, 0x13, 0x9d, 0x19, 0x13, + 0x42, 0x33, 0x57, 0x2b, 0xf7, 0xc8, 0x48, 0x02, + 0x13, 0x48, 0x50, 0xc8, 0x48, 0x02, 0x14, 0x48, + 0x50, 0xc8, 0x48, 0x02, 0x17, 0x49, 0x10, 0xc8, + 0x48, 0x02, 0x00, 0x0a, 0x82, 0x07, 0x04, 0x0d, + 0x88, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, + 0x18, 0x00, 0x81, 0x00, 0x0e, 0x9d, 0x41, 0xc0, + 0x19, 0x08, 0x09, 0x00, 0x49, 0x21, 0x63, 0x54, + 0x40, 0x50, 0x60, 0x19, 0x54, 0xab, 0xb3, 0x18, + 0x05, 0xf4, 0xef, 0xe2, 0x81, 0x17, 0x17, 0x16, + 0xc3, 0xbf, 0xcc +}; + +/* Base Station Subsystem GPRS Protocol: GSM A-I/F DTAP - Activate PDP Context Request */ +static const unsigned char bssgp_act_pdp_ctx_req[76] = { + 0x01, 0xef, 0xe2, 0xb7, 0x00, 0x00, 0x00, 0x04, + 0x08, 0x88, 0x11, 0x22, 0x33, 0x40, 0x50, 0x60, + 0x75, 0x30, 0x00, 0x80, 0x0e, 0x00, 0x35, 0x01, + 0xc0, 0x0d, 0x0a, 0x41, 0x05, 0x03, 0x0c, 0x00, + 0x00, 0x1f, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x02, 0x01, 0x21, 0x28, 0x03, + 0x02, 0x61, 0x62, 0x27, 0x14, 0x80, 0x80, 0x21, + 0x10, 0x01, 0x00, 0x00, 0x10, 0x81, 0x06, 0x00, + 0x00, 0x00, 0x00, 0x83, 0x06, 0x00, 0x00, 0x00, + 0x00, 0x5a, 0xff, 0x02 +}; static int gprs_process_message(struct gprs_ns_inst *nsi, const char *text, struct sockaddr_in *peer, const unsigned char* data, @@ -168,6 +243,37 @@ static void send_bssgp_reset_ack(struct gprs_ns_inst *nsi, send_ns_unitdata(nsi, "BVC_RESET_ACK", src_addr, 0, msg, sizeof(msg)); } +static void send_bssgp_suspend(struct gprs_ns_inst *nsi, + struct sockaddr_in *src_addr, + struct gprs_ra_id *raid) +{ + /* Base Station Subsystem GPRS Protocol, BSSGP SUSPEND */ + unsigned char msg[15] = { + 0x0b, 0x1f, 0x84, 0xcc, 0xd1, 0x75, 0x8b, 0x1b, + 0x86, 0x11, 0x22, 0x33, 0x40, 0x50, 0x60 + }; + + gsm48_construct_ra(msg + 9, raid); + + send_ns_unitdata(nsi, "BVC_SUSPEND", src_addr, 0, msg, sizeof(msg)); +} + +static void send_bssgp_suspend_ack(struct gprs_ns_inst *nsi, + struct sockaddr_in *src_addr, + struct gprs_ra_id *raid) +{ + /* Base Station Subsystem GPRS Protocol, BSSGP SUSPEND ACK */ + unsigned char msg[18] = { + 0x0c, 0x1f, 0x84, 0xcc, 0xd1, 0x75, 0x8b, 0x1b, + 0x86, 0x11, 0x22, 0x33, 0x40, 0x50, 0x60, 0x1d, + 0x81, 0x01 + }; + + gsm48_construct_ra(msg + 9, raid); + + send_ns_unitdata(nsi, "BVC_SUSPEND_ACK", src_addr, 0, msg, sizeof(msg)); +} + static void setup_ns(struct gprs_ns_inst *nsi, struct sockaddr_in *src_addr, uint16_t nsvci, uint16_t nsei) { @@ -687,6 +793,90 @@ static void test_gbproxy_ident_changes() gbprox_reset(); } +static void test_gbproxy_ra_patching() +{ + struct gprs_ns_inst *nsi = gprs_ns_instantiate(gprs_ns_callback, NULL); + struct sockaddr_in bss_peer[1] = {{0},}; + struct sockaddr_in sgsn_peer= {0}; + struct gprs_ra_id rai_bss = + {.mcc = 112, .mnc = 332, .lac = 16464, .rac = 96}; + struct gprs_ra_id rai_sgsn = + {.mcc = 123, .mnc = 456, .lac = 16464, .rac = 96}; + struct gprs_ra_id rai_unknown = + {.mcc = 1, .mnc = 99, .lac = 99, .rac = 96}; + + bssgp_nsi = nsi; + gbcfg.nsi = bssgp_nsi; + gbcfg.nsip_sgsn_nsei = SGSN_NSEI; + + sgsn_peer.sin_family = AF_INET; + sgsn_peer.sin_port = htons(32000); + sgsn_peer.sin_addr.s_addr = htonl(REMOTE_SGSN_ADDR); + + bss_peer[0].sin_family = AF_INET; + bss_peer[0].sin_port = htons(1111); + bss_peer[0].sin_addr.s_addr = htonl(REMOTE_BSS_ADDR); + + printf("--- Initialise SGSN ---\n\n"); + + connect_sgsn(nsi, &sgsn_peer); + gprs_dump_nsi(nsi); + + printf("--- Initialise BSS 1 ---\n\n"); + + setup_ns(nsi, &bss_peer[0], 0x1001, 0x1000); + setup_bssgp(nsi, &bss_peer[0], 0x1002); + gprs_dump_nsi(nsi); + gbprox_dump_peers(stdout, 0); + + send_bssgp_reset_ack(nsi, &sgsn_peer, 0x1002); + + send_bssgp_suspend(nsi, &bss_peer[0], &rai_bss); + send_bssgp_suspend_ack(nsi, &sgsn_peer, &rai_sgsn); + + gbprox_dump_global(stdout, 0); + gbprox_dump_peers(stdout, 0); + + printf("--- Send message from BSS 1 to SGSN, BVCI 0x1002 ---\n\n"); + + send_ns_unitdata(nsi, NULL, &bss_peer[0], 0x1002, + bssgp_attach_req, sizeof(bssgp_attach_req)); + + send_ns_unitdata(nsi, NULL, &sgsn_peer, 0x1002, + bssgp_attach_acc, sizeof(bssgp_attach_acc)); + + send_ns_unitdata(nsi, NULL, &bss_peer[0], 0x1002, + bssgp_ra_upd_req, sizeof(bssgp_ra_upd_req)); + + send_ns_unitdata(nsi, NULL, &sgsn_peer, 0x1002, + bssgp_ra_upd_acc, sizeof(bssgp_ra_upd_acc)); + + /* Replace APN */ + send_ns_unitdata(nsi, NULL, &bss_peer[0], 0x1002, + bssgp_act_pdp_ctx_req, sizeof(bssgp_act_pdp_ctx_req)); + + /* TODO: Re-configure to test APN IE removal */ + + /* Remove APN */ + send_ns_unitdata(nsi, NULL, &bss_peer[0], 0x1002, + bssgp_act_pdp_ctx_req, sizeof(bssgp_act_pdp_ctx_req)); + + gbprox_dump_global(stdout, 0); + gbprox_dump_peers(stdout, 0); + + printf("--- Bad cases ---\n\n"); + + send_bssgp_reset_ack(nsi, &sgsn_peer, 0x1eee); + send_bssgp_suspend_ack(nsi, &sgsn_peer, &rai_unknown); + + gbprox_dump_global(stdout, 0); + gbprox_dump_peers(stdout, 0); + + gprs_ns_destroy(nsi); + nsi = NULL; + gbprox_reset(); +} + static struct log_info info = {}; @@ -707,6 +897,7 @@ int main(int argc, char **argv) printf("===== GbProxy test START\n"); test_gbproxy(); test_gbproxy_ident_changes(); + test_gbproxy_ra_patching(); printf("===== GbProxy test END\n\n"); exit(EXIT_SUCCESS); diff --git a/openbsc/tests/gbproxy/gbproxy_test.ok b/openbsc/tests/gbproxy/gbproxy_test.ok index 3b25922..58add97 100644 --- a/openbsc/tests/gbproxy/gbproxy_test.ok +++ b/openbsc/tests/gbproxy/gbproxy_test.ok @@ -1518,5 +1518,273 @@ Peers: NS Transmission error : 2 NSEI 8192, BVCI 4098, not blocked, RAI 112-332-16464-96 NSEI mismatch : 1 +--- Initialise SGSN --- + +MESSAGE to SGSN at 0x05060708:32000, msg length 12 +02 00 81 01 01 82 01 01 04 82 01 00 + +PROCESSING RESET_ACK from 0x05060708:32000 +03 01 82 01 01 04 82 01 00 + +MESSAGE to SGSN at 0x05060708:32000, msg length 1 +0a + +result (RESET_ACK) = 1 + +PROCESSING ALIVE_ACK from 0x05060708:32000 +0b + +MESSAGE to SGSN at 0x05060708:32000, msg length 1 +06 + +result (ALIVE_ACK) = 1 + +PROCESSING UNBLOCK_ACK from 0x05060708:32000 +07 + +==> got signal NS_UNBLOCK, NS-VC 0x0101/5.6.7.8:32000 + +result (UNBLOCK_ACK) = 0 + +PROCESSING ALIVE from 0x05060708:32000 +0a + +MESSAGE to SGSN at 0x05060708:32000, msg length 1 +0b + +result (ALIVE) = 1 + +Current NS-VCIs: + VCI 0x0101, NSEI 0x0100, peer 0x05060708:32000 + NS-VC Block count : 1 + +--- Initialise BSS 1 --- + +Setup NS-VC: remote 0x01020304:1111, NSVCI 0x1001(4097), NSEI 0x1000(4096) + +PROCESSING RESET from 0x01020304:1111 +02 00 81 01 01 82 10 01 04 82 10 00 + +==> got signal NS_RESET, NS-VC 0x1001/1.2.3.4:1111 + +MESSAGE to BSS at 0x01020304:1111, msg length 9 +03 01 82 10 01 04 82 10 00 + +MESSAGE to BSS at 0x01020304:1111, msg length 1 +0a + +result (RESET) = 9 + +PROCESSING ALIVE from 0x01020304:1111 +0a + +MESSAGE to BSS at 0x01020304:1111, msg length 1 +0b + +result (ALIVE) = 1 + +PROCESSING UNBLOCK from 0x01020304:1111 +06 + +==> got signal NS_UNBLOCK, NS-VC 0x1001/1.2.3.4:1111 + +MESSAGE to BSS at 0x01020304:1111, msg length 1 +07 + +result (UNBLOCK) = 1 + +PROCESSING ALIVE_ACK from 0x01020304:1111 +0b + +result (ALIVE_ACK) = 0 + +Setup BSSGP: remote 0x01020304:1111, BVCI 0x1002(4098) + +PROCESSING BVC_RESET from 0x01020304:1111 +00 00 00 00 22 04 82 10 02 07 81 08 08 88 11 22 33 40 50 60 10 00 00 00 00 00 + +CALLBACK, event 0, msg length 22, bvci 0x0000 +22 04 82 10 02 07 81 08 08 88 11 22 33 40 50 60 10 00 00 00 00 00 + +NS UNITDATA MESSAGE to SGSN, BVCI 0x0000, msg length 22 +22 04 82 10 02 07 81 08 08 88 11 22 33 40 50 60 10 00 00 00 00 00 + +MESSAGE to SGSN at 0x05060708:32000, msg length 26 +00 00 00 00 22 04 82 10 02 07 81 08 08 88 11 22 33 40 50 60 10 00 00 00 00 00 + +result (BVC_RESET) = 26 + +Current NS-VCIs: + VCI 0x1001, NSEI 0x1000, peer 0x01020304:1111 + VCI 0x0101, NSEI 0x0100, peer 0x05060708:32000 + NS-VC Block count : 1 + +Peers: + NSEI 4096, BVCI 4098, not blocked, RAI 112-332-16464-96 +PROCESSING BVC_RESET_ACK from 0x05060708:32000 +00 00 00 00 23 04 82 10 02 + +CALLBACK, event 0, msg length 5, bvci 0x0000 +23 04 82 10 02 + +NS UNITDATA MESSAGE to BSS, BVCI 0x0000, msg length 5 +23 04 82 10 02 + +MESSAGE to BSS at 0x01020304:1111, msg length 9 +00 00 00 00 23 04 82 10 02 + +result (BVC_RESET_ACK) = 9 + +PROCESSING BVC_SUSPEND from 0x01020304:1111 +00 00 00 00 0b 1f 84 cc d1 75 8b 1b 86 11 22 33 40 50 60 + +CALLBACK, event 0, msg length 15, bvci 0x0000 +0b 1f 84 cc d1 75 8b 1b 86 11 22 33 40 50 60 + +NS UNITDATA MESSAGE to SGSN, BVCI 0x0000, msg length 15 +0b 1f 84 cc d1 75 8b 1b 86 11 22 33 40 50 60 + +MESSAGE to SGSN at 0x05060708:32000, msg length 19 +00 00 00 00 0b 1f 84 cc d1 75 8b 1b 86 11 22 33 40 50 60 + +result (BVC_SUSPEND) = 19 + +PROCESSING BVC_SUSPEND_ACK from 0x05060708:32000 +00 00 00 00 0c 1f 84 cc d1 75 8b 1b 86 21 63 54 40 50 60 1d 81 01 + +CALLBACK, event 0, msg length 18, bvci 0x0000 +0c 1f 84 cc d1 75 8b 1b 86 21 63 54 40 50 60 1d 81 01 + +NS UNITDATA MESSAGE to SGSN, BVCI 0x0000, msg length 24 +41 07 81 05 15 92 0c 1f 84 cc d1 75 8b 1b 86 21 63 54 40 50 60 1d 81 01 + +MESSAGE to SGSN at 0x05060708:32000, msg length 28 +00 00 00 00 41 07 81 05 15 92 0c 1f 84 cc d1 75 8b 1b 86 21 63 54 40 50 60 1d 81 01 + +result (BVC_SUSPEND_ACK) = 28 + +Gbproxy global: + Invalid Routing Area Identifier : 1 +Peers: + NSEI 4096, BVCI 4098, not blocked, RAI 112-332-16464-96 +--- Send message from BSS 1 to SGSN, BVCI 0x1002 --- + +PROCESSING UNITDATA from 0x01020304:1111 +00 00 10 02 01 bb c5 46 79 00 00 04 08 88 11 22 33 40 50 60 75 30 00 80 0e 00 34 01 c0 01 08 01 02 f5 e0 21 08 02 05 f4 fb c5 46 79 11 22 33 40 50 60 19 18 b3 43 2b 25 96 62 00 60 80 9a c2 c6 62 00 60 80 ba c8 c6 62 00 60 80 00 16 6d 01 + +CALLBACK, event 0, msg length 75, bvci 0x1002 +01 bb c5 46 79 00 00 04 08 88 11 22 33 40 50 60 75 30 00 80 0e 00 34 01 c0 01 08 01 02 f5 e0 21 08 02 05 f4 fb c5 46 79 11 22 33 40 50 60 19 18 b3 43 2b 25 96 62 00 60 80 9a c2 c6 62 00 60 80 ba c8 c6 62 00 60 80 00 16 6d 01 + +NS UNITDATA MESSAGE to SGSN, BVCI 0x1002, msg length 75 +01 bb c5 46 79 00 00 04 08 88 11 22 33 40 50 60 75 30 00 80 0e 00 34 01 c0 01 08 01 02 f5 e0 21 08 02 05 f4 fb c5 46 79 11 22 33 40 50 60 19 18 b3 43 2b 25 96 62 00 60 80 9a c2 c6 62 00 60 80 ba c8 c6 62 00 60 80 00 16 6d 01 + +MESSAGE to SGSN at 0x05060708:32000, msg length 79 +00 00 10 02 01 bb c5 46 79 00 00 04 08 88 11 22 33 40 50 60 75 30 00 80 0e 00 34 01 c0 01 08 01 02 f5 e0 21 08 02 05 f4 fb c5 46 79 11 22 33 40 50 60 19 18 b3 43 2b 25 96 62 00 60 80 9a c2 c6 62 00 60 80 ba c8 c6 62 00 60 80 00 16 6d 01 + +result (UNITDATA) = 79 + +PROCESSING UNITDATA from 0x05060708:32000 +00 00 10 02 00 bb c5 46 79 00 50 20 16 82 02 58 13 99 18 b3 43 2b 25 96 62 00 60 80 9a c2 c6 62 00 60 80 ba c8 c6 62 00 60 80 00 0a 82 08 02 0d 88 11 12 13 14 15 16 17 18 00 81 00 0e 9e 41 c0 05 08 02 01 49 04 21 63 54 40 50 60 19 cd d7 08 17 16 18 05 f4 fb c5 47 22 42 67 9a + +CALLBACK, event 0, msg length 88, bvci 0x1002 +00 bb c5 46 79 00 50 20 16 82 02 58 13 99 18 b3 43 2b 25 96 62 00 60 80 9a c2 c6 62 00 60 80 ba c8 c6 62 00 60 80 00 0a 82 08 02 0d 88 11 12 13 14 15 16 17 18 00 81 00 0e 9e 41 c0 05 08 02 01 49 04 21 63 54 40 50 60 19 cd d7 08 17 16 18 05 f4 fb c5 47 22 42 67 9a + +NS UNITDATA MESSAGE to BSS, BVCI 0x1002, msg length 88 +00 bb c5 46 79 00 50 20 16 82 02 58 13 99 18 b3 43 2b 25 96 62 00 60 80 9a c2 c6 62 00 60 80 ba c8 c6 62 00 60 80 00 0a 82 08 02 0d 88 11 12 13 14 15 16 17 18 00 81 00 0e 9e 41 c0 05 08 02 01 49 04 21 63 54 40 50 60 19 cd d7 08 17 16 18 05 f4 fb c5 47 22 42 67 9a + +MESSAGE to BSS at 0x01020304:1111, msg length 92 +00 00 10 02 00 bb c5 46 79 00 50 20 16 82 02 58 13 99 18 b3 43 2b 25 96 62 00 60 80 9a c2 c6 62 00 60 80 ba c8 c6 62 00 60 80 00 0a 82 08 02 0d 88 11 12 13 14 15 16 17 18 00 81 00 0e 9e 41 c0 05 08 02 01 49 04 21 63 54 40 50 60 19 cd d7 08 17 16 18 05 f4 fb c5 47 22 42 67 9a + +result (UNITDATA) = 92 + +PROCESSING UNITDATA from 0x01020304:1111 +00 00 10 02 01 af e2 80 6e 00 00 04 08 88 11 22 33 40 50 60 70 80 00 80 0e 00 3e 01 c0 15 08 08 10 11 22 33 40 50 60 1d 19 13 42 33 57 2b f7 c8 48 02 13 48 50 c8 48 02 14 48 50 c8 48 02 17 49 10 c8 48 02 00 19 8b b2 92 17 16 27 07 04 31 02 e5 e0 32 02 20 00 96 3e 97 + +CALLBACK, event 0, msg length 85, bvci 0x1002 +01 af e2 80 6e 00 00 04 08 88 11 22 33 40 50 60 70 80 00 80 0e 00 3e 01 c0 15 08 08 10 11 22 33 40 50 60 1d 19 13 42 33 57 2b f7 c8 48 02 13 48 50 c8 48 02 14 48 50 c8 48 02 17 49 10 c8 48 02 00 19 8b b2 92 17 16 27 07 04 31 02 e5 e0 32 02 20 00 96 3e 97 + +NS UNITDATA MESSAGE to SGSN, BVCI 0x1002, msg length 85 +01 af e2 80 6e 00 00 04 08 88 11 22 33 40 50 60 70 80 00 80 0e 00 3e 01 c0 15 08 08 10 11 22 33 40 50 60 1d 19 13 42 33 57 2b f7 c8 48 02 13 48 50 c8 48 02 14 48 50 c8 48 02 17 49 10 c8 48 02 00 19 8b b2 92 17 16 27 07 04 31 02 e5 e0 32 02 20 00 96 3e 97 + +MESSAGE to SGSN at 0x05060708:32000, msg length 89 +00 00 10 02 01 af e2 80 6e 00 00 04 08 88 11 22 33 40 50 60 70 80 00 80 0e 00 3e 01 c0 15 08 08 10 11 22 33 40 50 60 1d 19 13 42 33 57 2b f7 c8 48 02 13 48 50 c8 48 02 14 48 50 c8 48 02 17 49 10 c8 48 02 00 19 8b b2 92 17 16 27 07 04 31 02 e5 e0 32 02 20 00 96 3e 97 + +result (UNITDATA) = 89 + +PROCESSING UNITDATA from 0x05060708:32000 +00 00 10 02 00 af e2 80 6e 00 50 20 16 82 02 58 13 9d 19 13 42 33 57 2b f7 c8 48 02 13 48 50 c8 48 02 14 48 50 c8 48 02 17 49 10 c8 48 02 00 0a 82 07 04 0d 88 11 12 13 14 15 16 17 18 00 81 00 0e 9d 41 c0 19 08 09 00 49 21 63 54 40 50 60 19 54 ab b3 18 05 f4 ef e2 81 17 17 16 c3 bf cc + +CALLBACK, event 0, msg length 91, bvci 0x1002 +00 af e2 80 6e 00 50 20 16 82 02 58 13 9d 19 13 42 33 57 2b f7 c8 48 02 13 48 50 c8 48 02 14 48 50 c8 48 02 17 49 10 c8 48 02 00 0a 82 07 04 0d 88 11 12 13 14 15 16 17 18 00 81 00 0e 9d 41 c0 19 08 09 00 49 21 63 54 40 50 60 19 54 ab b3 18 05 f4 ef e2 81 17 17 16 c3 bf cc + +NS UNITDATA MESSAGE to BSS, BVCI 0x1002, msg length 91 +00 af e2 80 6e 00 50 20 16 82 02 58 13 9d 19 13 42 33 57 2b f7 c8 48 02 13 48 50 c8 48 02 14 48 50 c8 48 02 17 49 10 c8 48 02 00 0a 82 07 04 0d 88 11 12 13 14 15 16 17 18 00 81 00 0e 9d 41 c0 19 08 09 00 49 21 63 54 40 50 60 19 54 ab b3 18 05 f4 ef e2 81 17 17 16 c3 bf cc + +MESSAGE to BSS at 0x01020304:1111, msg length 95 +00 00 10 02 00 af e2 80 6e 00 50 20 16 82 02 58 13 9d 19 13 42 33 57 2b f7 c8 48 02 13 48 50 c8 48 02 14 48 50 c8 48 02 17 49 10 c8 48 02 00 0a 82 07 04 0d 88 11 12 13 14 15 16 17 18 00 81 00 0e 9d 41 c0 19 08 09 00 49 21 63 54 40 50 60 19 54 ab b3 18 05 f4 ef e2 81 17 17 16 c3 bf cc + +result (UNITDATA) = 95 + +PROCESSING UNITDATA from 0x01020304:1111 +00 00 10 02 01 ef e2 b7 00 00 00 04 08 88 11 22 33 40 50 60 75 30 00 80 0e 00 35 01 c0 0d 0a 41 05 03 0c 00 00 1f 10 00 00 00 00 00 00 00 00 02 01 21 28 03 02 61 62 27 14 80 80 21 10 01 00 00 10 81 06 00 00 00 00 83 06 00 00 00 00 5a ff 02 + +CALLBACK, event 0, msg length 76, bvci 0x1002 +01 ef e2 b7 00 00 00 04 08 88 11 22 33 40 50 60 75 30 00 80 0e 00 35 01 c0 0d 0a 41 05 03 0c 00 00 1f 10 00 00 00 00 00 00 00 00 02 01 21 28 03 02 61 62 27 14 80 80 21 10 01 00 00 10 81 06 00 00 00 00 83 06 00 00 00 00 5a ff 02 + +NS UNITDATA MESSAGE to SGSN, BVCI 0x1002, msg length 76 +01 ef e2 b7 00 00 00 04 08 88 11 22 33 40 50 60 75 30 00 80 0e 00 35 01 c0 0d 0a 41 05 03 0c 00 00 1f 10 00 00 00 00 00 00 00 00 02 01 21 28 03 02 61 62 27 14 80 80 21 10 01 00 00 10 81 06 00 00 00 00 83 06 00 00 00 00 5a ff 02 + +MESSAGE to SGSN at 0x05060708:32000, msg length 80 +00 00 10 02 01 ef e2 b7 00 00 00 04 08 88 11 22 33 40 50 60 75 30 00 80 0e 00 35 01 c0 0d 0a 41 05 03 0c 00 00 1f 10 00 00 00 00 00 00 00 00 02 01 21 28 03 02 61 62 27 14 80 80 21 10 01 00 00 10 81 06 00 00 00 00 83 06 00 00 00 00 5a ff 02 + +result (UNITDATA) = 80 + +PROCESSING UNITDATA from 0x01020304:1111 +00 00 10 02 01 ef e2 b7 00 00 00 04 08 88 11 22 33 40 50 60 75 30 00 80 0e 00 35 01 c0 0d 0a 41 05 03 0c 00 00 1f 10 00 00 00 00 00 00 00 00 02 01 21 28 03 02 61 62 27 14 80 80 21 10 01 00 00 10 81 06 00 00 00 00 83 06 00 00 00 00 5a ff 02 + +CALLBACK, event 0, msg length 76, bvci 0x1002 +01 ef e2 b7 00 00 00 04 08 88 11 22 33 40 50 60 75 30 00 80 0e 00 35 01 c0 0d 0a 41 05 03 0c 00 00 1f 10 00 00 00 00 00 00 00 00 02 01 21 28 03 02 61 62 27 14 80 80 21 10 01 00 00 10 81 06 00 00 00 00 83 06 00 00 00 00 5a ff 02 + +NS UNITDATA MESSAGE to SGSN, BVCI 0x1002, msg length 76 +01 ef e2 b7 00 00 00 04 08 88 11 22 33 40 50 60 75 30 00 80 0e 00 35 01 c0 0d 0a 41 05 03 0c 00 00 1f 10 00 00 00 00 00 00 00 00 02 01 21 28 03 02 61 62 27 14 80 80 21 10 01 00 00 10 81 06 00 00 00 00 83 06 00 00 00 00 5a ff 02 + +MESSAGE to SGSN at 0x05060708:32000, msg length 80 +00 00 10 02 01 ef e2 b7 00 00 00 04 08 88 11 22 33 40 50 60 75 30 00 80 0e 00 35 01 c0 0d 0a 41 05 03 0c 00 00 1f 10 00 00 00 00 00 00 00 00 02 01 21 28 03 02 61 62 27 14 80 80 21 10 01 00 00 10 81 06 00 00 00 00 83 06 00 00 00 00 5a ff 02 + +result (UNITDATA) = 80 + +Gbproxy global: + Invalid Routing Area Identifier : 1 +Peers: + NSEI 4096, BVCI 4098, not blocked, RAI 112-332-16464-96 +--- Bad cases --- + +PROCESSING BVC_RESET_ACK from 0x05060708:32000 +00 00 00 00 23 04 82 1e ee + +CALLBACK, event 0, msg length 5, bvci 0x0000 +23 04 82 1e ee + +result (BVC_RESET_ACK) = -2 + +PROCESSING BVC_SUSPEND_ACK from 0x05060708:32000 +00 00 00 00 0c 1f 84 cc d1 75 8b 1b 86 00 f1 99 00 63 60 1d 81 01 + +CALLBACK, event 0, msg length 18, bvci 0x0000 +0c 1f 84 cc d1 75 8b 1b 86 00 f1 99 00 63 60 1d 81 01 + +NS UNITDATA MESSAGE to SGSN, BVCI 0x0000, msg length 24 +41 07 81 05 15 92 0c 1f 84 cc d1 75 8b 1b 86 00 f1 99 00 63 60 1d 81 01 + +MESSAGE to SGSN at 0x05060708:32000, msg length 28 +00 00 00 00 41 07 81 05 15 92 0c 1f 84 cc d1 75 8b 1b 86 00 f1 99 00 63 60 1d 81 01 + +result (BVC_SUSPEND_ACK) = 28 + +Gbproxy global: + Invalid BVC Identifier : 1 + Invalid Routing Area Identifier : 2 +Peers: + NSEI 4096, BVCI 4098, not blocked, RAI 112-332-16464-96 ===== GbProxy test END -- 1.9.1 From Norbert.Englberger at unibw.de Mon Jul 7 11:39:06 2014 From: Norbert.Englberger at unibw.de (Norbert Englberger) Date: Mon, 7 Jul 2014 13:39:06 +0200 Subject: Need help with configuration of Timeslots and of multible USRPs Message-ID: Hello everybody, after starting on my new Job at an University I have been tasked to build up an BTS for our students. Being a complete noob to both Linux and GSM it took me some time, but I finally got OpenBSC and Osmo-BTS up and running on Ubuntu Linux 12.04 with our ETTUS N210. After doing some experiments with this setup, our students now ask me to do some changes which I couldn't figure out yet, how to do. 1. The students told me, that OpenBSC doesn't behave like all the BTS from commercial Providers they analysed: The say that on commercial nets at the beginning of a phone call there will be send an "Immediate assignment" sending the MS always to a SDCCH on TS 1 or TS2 where the encryption will be startet. After establishing the encryption another "Immediate assignment" will occour and send the MS to a Traffic Channel (which also contains the FACCH / SACCH) for the actual Communication. OpenBSC also sends the "Immediate assignment" on TS0 but sends the MS directly to Timeslot with a Traffic Channel where all the signalling, like encryption, will be done in the SACCH. Is there any way to configure OsmoBSC to behave like the commercial BTS the students described? 2. I have been asked if I could enable "Frequency Hopping" Right now I already fail to bring up a second TRX with OpenBSC. I start 2 instances of "osmo-trx" with 2 differents IP-Addresses but the same port, after that I start "osmobts-trx" with the "-t 2" parameter. OpenBSC seems to see both USRPs but the LED'S an the USRPs indicate that only one is completely powered up and transmitting (a quick check with an Motorola with RSSI also shows only one ARFC). So how do I have to start "osmo-trx" to enable transmitting on both URSPs as TRX0 and TRX1 in one BTS? After that, is it possible to configure "Frequency hopping" with this setup? (Because when I changed the value "hopping enabled" of the timeslots in open-bts.cfg to "1" I get a message that this type of BTS does not support hopping) I hope that anyone can clarify those two points to me. Thanks in advance Norbie From holger at freyther.de Mon Jul 7 20:00:21 2014 From: holger at freyther.de (Holger Hans Peter Freyther) Date: Mon, 7 Jul 2014 22:00:21 +0200 Subject: Need help with configuration of Timeslots and of multible USRPs In-Reply-To: References: Message-ID: <20140707200021.GP32605@xiaoyu.lan> On Mon, Jul 07, 2014 at 01:39:06PM +0200, Norbert Englberger wrote: > Hello everybody, Hi, > > 1. The students told me, that OpenBSC doesn't behave like all the BTS from > commercial Providers they analysed: > The say that on commercial nets at the beginning of a phone call there will > be send an "Immediate assignment" sending the MS always to a SDCCH on TS 1 > or TS2 where the encryption will be startet. After establishing the > encryption another "Immediate assignment" will occour and send the MS to a > Traffic Channel (which also contains the FACCH / SACCH) for the actual > Communication. > OpenBSC also sends the "Immediate assignment" on TS0 but sends the MS > directly to Timeslot with a Traffic Channel where all the signalling, like > encryption, will be done in the SACCH. > Is there any way to configure OsmoBSC to behave like the commercial BTS the > students described? it is not a question of BTS but the BSC. The role of the BSC is to manage the channels. Inside src/libbsc/gsm_04_08_utils.c you will see a table that determines how the BSC/NITB will respond to "channel request" inside the RACH request by the phone. E.g. if you change get_ctype_by_chreq to always return LCHAN_SDCCH you should be close to the behavior you have described. From alexander.chemeris at gmail.com Wed Jul 9 09:33:29 2014 From: alexander.chemeris at gmail.com (Alexander Chemeris) Date: Wed, 9 Jul 2014 13:33:29 +0400 Subject: Need help with configuration of Timeslots and of multible USRPs In-Reply-To: References: Message-ID: Hi Norbert, 07 ???? 2014 ?. 15:40 ???????????? "Norbert Englberger" < Norbert.Englberger at unibw.de> ???????: > > 2. I have been asked if I could enable "Frequency Hopping" > Right now I already fail to bring up a second TRX with OpenBSC. > I start 2 instances of "osmo-trx" with 2 differents IP-Addresses but the > same port, after that I start "osmobts-trx" with the "-t 2" parameter. > OpenBSC seems to see both USRPs but the LED'S an the USRPs indicate that > only one is completely powered up and transmitting (a quick check with an > Motorola with RSSI also shows only one ARFC). > So how do I have to start "osmo-trx" to enable transmitting on both URSPs > as TRX0 and TRX1 in one BTS? > After that, is it possible to configure "Frequency hopping" with this setup? > (Because when I changed the value "hopping enabled" of the timeslots in > open-bts.cfg to "1" I get a message that this type of BTS does not support > hopping) Using two osmo-trx's or two devices with a single osmo-trx is not supported at this moment and there are no current plans to support this configuration, AFAIK. That said, we're working on supporting frequency hopping with a single device. I expect this to be ready for testing in the next few months. Please excuse typos. Written with a touchscreen keyboard. -- Regards, Alexander Chemeris CEO Fairwaves, Inc. https://fairwaves.co -------------- next part -------------- An HTML attachment was scrubbed... URL: From Norbert.Englberger at unibw.de Tue Jul 8 12:31:11 2014 From: Norbert.Englberger at unibw.de (Norbert Englberger) Date: Tue, 8 Jul 2014 14:31:11 +0200 Subject: Need help with configuration of Timeslots and of multible USRPs Message-ID: Hello again, Holger Hans Peter Freyther wrote: > it is not a question of BTS but the BSC. The role of the BSC is to manage the > channels. Inside src/libbsc/gsm_04_08_utils.c you will see a table that > determines how the BSC/NITB will respond to "channel request" inside the > RACH request by the phone. > > E.g. if you change get_ctype_by_chreq to always return LCHAN_SDCCH you > should be close to the behavior you have described. > First off all: Thank you for your fast response. I was hoping that it would be enough to change the settings in the open-bsc.cfg and I wouldn't have to temper the source code, as I said, I'm new to all the GSM stuff and Linux. I had a quick look at the code and just tried to comment out everything in "get_ctype_by_chreq" and always return LCHAN_SDCCH as you suggested. While testing this setup I saw, that The "Immediate assignment" now sends the calling MS to TS 1 (which is configured as SDCCH/8) subslot 0 and starts encryption and sends SI5 and SI6 messages on this timeslot/subslot. Also the called MS gets "Immediate assignment" and is sent to TS 1 subslot 1, encryption starts and so on. Now the called MS sends "Call Confirmed", but shortly after this the channels are released. (The called MS wasn't ringing at all) Am I right, that this is because both MS are yet sticking on the SDCCH and are not going to a Transport channel? (would make sense, because I always return SDCCH when the BSC wants to change channel) I think I have to change the Table " ctype_by_chreq" or to find a way to insert another "Immediate Assignmend" between "encryption" and "call confirmed" So I think I'll have to study the source code for a while, Again thanks for the hint where to start. [Norbert Englberger] From alexander.chemeris at gmail.com Wed Jul 9 09:21:28 2014 From: alexander.chemeris at gmail.com (Alexander Chemeris) Date: Wed, 9 Jul 2014 13:21:28 +0400 Subject: Need help with configuration of Timeslots and of multible USRPs In-Reply-To: References: Message-ID: Hi Norbert, 08 ???? 2014 ?. 16:34 ???????????? "Norbert Englberger" < Norbert.Englberger at unibw.de> ???????: > > > Hello again, > > Holger Hans Peter Freyther wrote: > > > it is not a question of BTS but the BSC. The role of the BSC is to manage > the > > channels. Inside src/libbsc/gsm_04_08_utils.c you will see a table that > > determines how the BSC/NITB will respond to "channel request" inside the > > RACH request by the phone. > > > > E.g. if you change get_ctype_by_chreq to always return LCHAN_SDCCH you > > should be close to the behavior you have described. > > > > First off all: Thank you for your fast response. > > I was hoping that it would be enough to change the settings in the > open-bsc.cfg and I wouldn't have to temper the source code, as I said, I'm > new to all the GSM stuff and Linux. Just for the sake of full understanding, what you're asking for is called "Late Assignment". Check the specs for the exact details or Wikipedia for a brief explanation: http://en.m.wikipedia.org/wiki/Um_interface#Mobile-Originating_Call_.28MOC.29_establishment I don't have the code near me at the moment, but this might be implemented in the "jolly" branch. Please excuse typos. Written with a touchscreen keyboard. -- Regards, Alexander Chemeris CEO Fairwaves, Inc. https://fairwaves.co -------------- next part -------------- An HTML attachment was scrubbed... URL: From alexander.chemeris at gmail.com Thu Jul 10 15:24:28 2014 From: alexander.chemeris at gmail.com (Alexander Chemeris) Date: Thu, 10 Jul 2014 19:24:28 +0400 Subject: Need help with configuration of Timeslots and of multible USRPs In-Reply-To: References: Message-ID: Norbert, On Thu, Jul 10, 2014 at 11:01 AM, Norbert Englberger wrote: > Alexander Chemeris wrote: >>Just for the sake of full understanding, what you're asking for is called "Late Assignment". Check the specs for the exact details or Wikipedia for a brief explanation: >>http://en.m.wikipedia.org/wiki/Um_interface#Mobile-Originating_Call_.28MOC.29_establishment >>I don't have the code near me at the moment, but this might be implemented in the "jolly" branch. > > i was already using the jolly/testing branch. > > Now that you hinted me to the "Late Assignment" I googled that and found that there is a "jolly/new_handover" branch using it. > Is this still the branch I should use, because when I tried to compile it, make failed. (I am right now trying to google if there are > other dependencies I have to change the branch and to recompile) I have never worked with this branch, so can't comment unfortunately. AFAIK, this branch is not being used in real environments, so it's most likely bit-rotten. My suggestion is to take the implementation there as an inspiration and re-implement it for master. That would make a good work for one of your students probably. Please don't move the conversation into private and keep the mailing list CC'ed. -- Regards, Alexander Chemeris. CEO, Fairwaves, Inc. https://fairwaves.co From holger at freyther.de Thu Jul 10 07:13:11 2014 From: holger at freyther.de (Holger Hans Peter Freyther) Date: Thu, 10 Jul 2014 09:13:11 +0200 Subject: [RFC/PATCH] tlv/msgb: Be able to generate and parse TLV as used by LLDP Message-ID: <1404976392-22876-1-git-send-email-holger@freyther.de> Hi! we have the need to generate and parse LLDP frames and would like to use the TLV infrastructure of libosmocore for it. In LLDP the tag is only 7bit and the length is 9bit long. To make this work with the tlv parsing routines we need to shift the tag. But this means that when somebody is a tlv_definition with the T7L9 type and others we might match the wrong thing. I would like to include the feature as it is right now. The alternative would be to create a separate tlv_parse and tlv_parse_one routine for the other type. comments? holger From holger at freyther.de Thu Jul 10 07:13:12 2014 From: holger at freyther.de (Holger Hans Peter Freyther) Date: Thu, 10 Jul 2014 09:13:12 +0200 Subject: [PATCH] tlv/msgb: Be able to generate and parse TLV as used by LLDP In-Reply-To: <1404976392-22876-1-git-send-email-holger@freyther.de> References: <1404976392-22876-1-git-send-email-holger@freyther.de> Message-ID: <1404976392-22876-2-git-send-email-holger@freyther.de> From: Daniel Laszlo Sitzer The Link Layer Discovery Protocol is using a Tag Length Value (TLV) structure. What is different is that the tag and length do not stop at byte boundaries. This commit introduces methods to msgb and tlv to be able to create such a tag/length header and a way to parse it using the tlv_parse routine. When it comes to parsing we have an issue that the new TLV_TYPE_T7L9V should not be mixed with the other types inside the same tlv definition. This is due the bitshifting required to identify the tag. The code likely requires work on big-endian machines but so does most of the other code as well. --- .gitignore | 1 + include/osmocom/gsm/tlv.h | 14 ++++ src/gsm/tlv_parser.c | 19 +++++ tests/Makefile.am | 8 +- tests/testsuite.at | 6 ++ tests/tlv/tlv_test.c | 205 ++++++++++++++++++++++++++++++++++++++++++++++ tests/tlv/tlv_test.ok | 8 ++ 7 files changed, 259 insertions(+), 2 deletions(-) create mode 100644 tests/tlv/tlv_test.c create mode 100644 tests/tlv/tlv_test.ok diff --git a/.gitignore b/.gitignore index 1299028..4a83bf1 100644 --- a/.gitignore +++ b/.gitignore @@ -78,6 +78,7 @@ tests/loggingrb/loggingrb_test tests/ringbuf/ringbuf_test tests/strrb/strrb_test tests/vty/vty_test +tests/tlv/tlv_test utils/osmo-arfcn utils/osmo-auc-gen diff --git a/include/osmocom/gsm/tlv.h b/include/osmocom/gsm/tlv.h index fda1810..9add360 100644 --- a/include/osmocom/gsm/tlv.h +++ b/include/osmocom/gsm/tlv.h @@ -213,6 +213,19 @@ static inline uint8_t *msgb_l16tv_put(struct msgb *msg, uint16_t len, uint8_t ta return buf + len; } +/*! \brief put (append) a T7L9 field to \ref msgb */ +static inline uint8_t *msgb_t7l9_put(struct msgb *msg, uint8_t tag, uint16_t len) +{ + uint16_t tl; + + tl = tag << 9; + tl |= len & 0x1FF; + + msgb_put_u16(msg, tl); + + return msg->tail; +} + /*! \brief put (append) a V field */ static inline uint8_t *v_put(uint8_t *buf, uint8_t val) { @@ -376,6 +389,7 @@ enum tlv_type { TLV_TYPE_TvLV, /*!< \brief tag, variable length, value */ TLV_TYPE_SINGLE_TV, /*!< \brief tag and value (both 4 bit) in 1 byte */ TLV_TYPE_vTvLV_GAN, /*!< \brief variable-length tag, variable-length length */ + TLV_TYPE_T7L9V, /*!< \brief 7 bit tag, 9 bit length, value */ }; /*! \brief Definition of a single IE (Information Element) */ diff --git a/src/gsm/tlv_parser.c b/src/gsm/tlv_parser.c index 8cb2139..852c1a7 100644 --- a/src/gsm/tlv_parser.c +++ b/src/gsm/tlv_parser.c @@ -51,6 +51,25 @@ int tlv_parse_one(uint8_t *o_tag, uint16_t *o_len, const uint8_t **o_val, return 1; } + /* + * Check if this could be a T7L9V tag. Do it by + * shifting it to the right once. Note that this + * means that mixing T7L9V with other tags is not + * possible. + */ + if (def->def[tag >> 1].type == TLV_TYPE_T7L9V) { + *o_tag = tag >> 1; + if (buf + 1 > buf + buf_len) + return -1; + *o_len = (tag & 0x1) << 8; + *o_len |= *(buf + 1); + *o_val = buf + 2; + len = *o_len + 2; + if (len > buf_len) + return -2; + return len; + } + /* FIXME: use tables for knwon IEI */ switch (def->def[tag].type) { case TLV_TYPE_T: diff --git a/tests/Makefile.am b/tests/Makefile.am index ea4bf9c..5c21561 100644 --- a/tests/Makefile.am +++ b/tests/Makefile.am @@ -7,7 +7,8 @@ check_PROGRAMS = timer/timer_test sms/sms_test ussd/ussd_test \ gb/bssgp_fc_test gb/gprs_ns_test kasumi/kasumi_test \ logging/logging_test fr/fr_test \ loggingrb/loggingrb_test strrb/strrb_test \ - vty/vty_test comp128/comp128_test utils/utils_test + vty/vty_test comp128/comp128_test utils/utils_test \ + tlv/tlv_test if ENABLE_MSGFILE check_PROGRAMS += msgfile/msgfile_test @@ -80,6 +81,9 @@ strrb_strrb_test_LDADD = $(top_builddir)/src/libosmocore.la vty_vty_test_SOURCES = vty/vty_test.c vty_vty_test_LDADD = $(top_builddir)/src/vty/libosmovty.la $(top_builddir)/src/libosmocore.la +tlv_tlv_test_SOURCES = tlv/tlv_test.c +tlv_tlv_test_LDADD = $(top_builddir)/src/libosmocore.la $(top_builddir)/src/gsm/libosmogsm.la + # The `:;' works around a Bash 3.2 bug when the output is not writeable. $(srcdir)/package.m4: $(top_srcdir)/configure.ac @@ -112,7 +116,7 @@ EXTRA_DIST = testsuite.at $(srcdir)/package.m4 $(TESTSUITE) \ fr/fr_test.ok loggingrb/logging_test.ok \ loggingrb/logging_test.err strrb/strrb_test.ok \ vty/vty_test.ok comp128/comp128_test.ok \ - utils/utils_test.ok + utils/utils_test.ok tlv/tlv_test.ok DISTCLEANFILES = atconfig diff --git a/tests/testsuite.at b/tests/testsuite.at index 7ce2ee8..45e5f8e 100644 --- a/tests/testsuite.at +++ b/tests/testsuite.at @@ -118,6 +118,12 @@ cat $abs_srcdir/vty/vty_test.ok > expout AT_CHECK([$abs_top_builddir/tests/vty/vty_test], [0], [expout], [ignore]) AT_CLEANUP +AT_SETUP([tlv]) +AT_KEYWORDS([tlv]) +cat $abs_srcdir/tlv/tlv_test.ok > expout +AT_CHECK([$abs_top_builddir/tests/tlv/tlv_test], [0], [expout], [ignore]) +AT_CLEANUP + AT_SETUP([gprs-ns]) AT_KEYWORDS([gprs-ns]) cat $abs_srcdir/gb/gprs_ns_test.ok > expout diff --git a/tests/tlv/tlv_test.c b/tests/tlv/tlv_test.c new file mode 100644 index 0000000..8d48e78 --- /dev/null +++ b/tests/tlv/tlv_test.c @@ -0,0 +1,205 @@ +/* Copyright (C) 2014 sysmocom - s.f.m.c. GmbH. All rights reserved + * Author: Daniel Laszlo Sitzer + * + * This program is iree software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 3 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with this program; if not, write to the Free Software Foundation, Inc., + * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. + * + */ + +#include +#include +#include +#include + +static const struct tlv_definition dummy_tlvdef = { + .def = { + [1] = { TLV_TYPE_T7L9V }, + [4] = { TLV_TYPE_TV }, + }, +}; + +static const struct tlv_definition lldp_tlvdef = { + .def = { + [1] = { TLV_TYPE_T7L9V }, + [2] = { TLV_TYPE_T7L9V }, + [3] = { TLV_TYPE_T7L9V }, + [0] = { TLV_TYPE_T7L9V }, + }, +}; + +static void test_lldp_tlv(void) +{ + struct msgb *m; + struct tlv_parsed tp; + int nparsed; + uint8_t *res; + + printf("%s\n", __func__); + + m = msgb_alloc(128, "lldp_tlv"); + + res = msgb_t7l9_put(m, 1, 7); + OSMO_ASSERT(m->len == 2); + OSMO_ASSERT(m->data[0] == 2); + OSMO_ASSERT(m->data[1] == 7); + OSMO_ASSERT(res == &m->data[2]); + + m->len += 7; + m->tail += 7; + + msgb_tv_put(m, 4, 0x55); + + nparsed = tlv_parse(&tp, &dummy_tlvdef, m->data, m->len, 0, 0); + OSMO_ASSERT(nparsed == 2); + OSMO_ASSERT(!TLVP_PRESENT(&tp, 0)); + OSMO_ASSERT(TLVP_PRESENT(&tp, 1)); + OSMO_ASSERT(TLVP_PRESENT(&tp, 4)); + OSMO_ASSERT(TLVP_LEN(&tp, 1) == 7); + OSMO_ASSERT(TLVP_VAL(&tp, 1) == &m->data[2]); + OSMO_ASSERT(*TLVP_VAL(&tp, 4) == 0x55); + + msgb_free(m); +} + +static void test_lldp_tlv_col(void) +{ + struct msgb *m; + struct tlv_parsed tp; + int nparsed; + uint8_t *res; + + printf("%s\n", __func__); + + m = msgb_alloc(512, "lldp_tlv"); + + res = msgb_t7l9_put(m, 1, 256); + OSMO_ASSERT(m->len == 2); + OSMO_ASSERT(m->data[0] == 3); + OSMO_ASSERT(m->data[1] == 0); + OSMO_ASSERT(res == &m->data[2]); + + m->len += 256; + m->tail += 256; + + msgb_tv_put(m, 4, 0xAA); + + nparsed = tlv_parse(&tp, &dummy_tlvdef, m->data, m->len, 0, 0); + OSMO_ASSERT(nparsed == 2); + OSMO_ASSERT(!TLVP_PRESENT(&tp, 0)); + OSMO_ASSERT(TLVP_PRESENT(&tp, 1)); + OSMO_ASSERT(TLVP_PRESENT(&tp, 4)); + OSMO_ASSERT(TLVP_LEN(&tp, 1) == 256); + OSMO_ASSERT(TLVP_VAL(&tp, 1) == &m->data[2]); + OSMO_ASSERT(*TLVP_VAL(&tp, 4) == 0xAA); + + msgb_free(m); +} + +static struct msgb *create_lldp_frame(const uint8_t *mac) +{ + int i; + struct msgb *m; + + m = msgb_alloc(512, "lldp_tlv"); + + /* Chassis ID TLV */ + msgb_t7l9_put(m, 1, 7); + msgb_put_u8(m, 4); /* Chassis ID Subtype: MAC address */ + for (i = 0; i < 6; ++i) + msgb_put_u8(m, mac[i]); + + /* Port ID TLV */ + msgb_t7l9_put(m, 2, 7); + msgb_put_u8(m, 3); /* Port ID Subtype: MAC address */ + for (i = 0; i < 6; ++i) + msgb_put_u8(m, mac[i]); + + /* TTL TLV */ + msgb_t7l9_put(m, 3, 2); + msgb_put_u16(m, 127); + + /* EOLLDPDU TLV */ + msgb_t7l9_put(m, 0, 0); + + return m; +} + +static void test_lldp_tlv_lldpdu(void) +{ + struct msgb *m; + struct tlv_parsed tp; + int nparsed; + const uint8_t mac[] = {0xF0, 0xDE, 0xF1, 0x02, 0x43, 0x01}; + + printf("%s\n", __func__); + + m = create_lldp_frame(mac); + + nparsed = tlv_parse(&tp, &lldp_tlvdef, m->data, m->len, 0, 0); + OSMO_ASSERT(nparsed == 4); + OSMO_ASSERT(TLVP_PRESENT(&tp, 1)); + OSMO_ASSERT(TLVP_PRESENT(&tp, 2)); + OSMO_ASSERT(TLVP_PRESENT(&tp, 3)); + OSMO_ASSERT(TLVP_PRESENT(&tp, 0)); + OSMO_ASSERT(TLVP_LEN(&tp, 1) == 1 + ARRAY_SIZE(mac)); + OSMO_ASSERT(TLVP_LEN(&tp, 2) == 1 + ARRAY_SIZE(mac)); + OSMO_ASSERT(TLVP_LEN(&tp, 3) == 2); + OSMO_ASSERT(TLVP_LEN(&tp, 0) == 0); + OSMO_ASSERT(*TLVP_VAL(&tp, 1) == 4); + OSMO_ASSERT(*TLVP_VAL(&tp, 2) == 3); + OSMO_ASSERT(memcmp(TLVP_VAL(&tp, 1)+1, mac, ARRAY_SIZE(mac)) == 0); + OSMO_ASSERT(memcmp(TLVP_VAL(&tp, 2)+1, mac, ARRAY_SIZE(mac)) == 0); + OSMO_ASSERT(*TLVP_VAL(&tp, 3) == 0); + OSMO_ASSERT(*(TLVP_VAL(&tp, 3)+1) == 127); + + msgb_free(m); +} + +static void test_lldp_truncated(void) +{ + struct msgb *m; + const uint8_t mac[] = {0xF0, 0xDE, 0xF1, 0x02, 0x43, 0x01}; + size_t i; + int success = 0; + + printf("%s\n", __func__); + + m = create_lldp_frame(mac); + + /* test truncated messages and expect the parse failure */ + for (i = m->len; i > 0; --i) { + int nparsed; + struct tlv_parsed tp; + + nparsed = tlv_parse(&tp, &lldp_tlvdef, m->data, i, 0, 0); + if (nparsed >= 0) { + printf("Success on %zu with %d\n", i, nparsed); + success += 1; + } + } + + /* if we truncate a frame enough it becomes parable again */ + OSMO_ASSERT(success == 4); + msgb_free(m); +} + +int main(int argc, char *argv[]) +{ + test_lldp_tlv(); + test_lldp_tlv_col(); + test_lldp_tlv_lldpdu(); + test_lldp_truncated(); + + return EXIT_SUCCESS; +} diff --git a/tests/tlv/tlv_test.ok b/tests/tlv/tlv_test.ok new file mode 100644 index 0000000..e038472 --- /dev/null +++ b/tests/tlv/tlv_test.ok @@ -0,0 +1,8 @@ +test_lldp_tlv +test_lldp_tlv_col +test_lldp_tlv_lldpdu +test_lldp_truncated +Success on 24 with 4 +Success on 22 with 3 +Success on 18 with 2 +Success on 9 with 1 -- 2.0.0.rc2 From Max.Suraev at fairwaves.co Thu Jul 10 09:38:34 2014 From: Max.Suraev at fairwaves.co (=?UTF-8?B?4piO?=) Date: Thu, 10 Jul 2014 11:38:34 +0200 Subject: [PATCH] tlv/msgb: Be able to generate and parse TLV as used by LLDP In-Reply-To: <1404976392-22876-2-git-send-email-holger@freyther.de> References: <1404976392-22876-1-git-send-email-holger@freyther.de> <1404976392-22876-2-git-send-email-holger@freyther.de> Message-ID: <53BE5F1A.3080708@fairwaves.co> Interesting, I didn't know we support LLDP. Could you highlight use-case: whom are we talking to over LLDP? -- best regards, Max, http://fairwaves.co From peter at stuge.se Thu Jul 10 12:03:43 2014 From: peter at stuge.se (Peter Stuge) Date: Thu, 10 Jul 2014 14:03:43 +0200 Subject: [PATCH] tlv/msgb: Be able to generate and parse TLV as used by LLDP In-Reply-To: <1404976392-22876-2-git-send-email-holger@freyther.de> References: <1404976392-22876-1-git-send-email-holger@freyther.de> <1404976392-22876-2-git-send-email-holger@freyther.de> Message-ID: <20140710120343.32448.qmail@stuge.se> Holger Hans Peter Freyther wrote: > +++ b/src/gsm/tlv_parser.c > @@ -51,6 +51,25 @@ int tlv_parse_one(uint8_t *o_tag, uint16_t *o_len, const uint8_t **o_val, > return 1; > } > > + /* > + * Check if this could be a T7L9V tag. Do it by > + * shifting it to the right once. Note that this > + * means that mixing T7L9V with other tags is not > + * possible. Why not explicitly specify to do this test for each tag? Ie. leave the old function as-is, add a new function with the T7L9V heuristic, and use the new function only at call sites where T7L9V may actually be encountered. //Peter From holger at freyther.de Thu Jul 10 18:46:05 2014 From: holger at freyther.de (Holger Hans Peter Freyther) Date: Thu, 10 Jul 2014 20:46:05 +0200 Subject: [PATCH] tlv/msgb: Be able to generate and parse TLV as used by LLDP In-Reply-To: <20140710120343.32448.qmail@stuge.se> References: <1404976392-22876-1-git-send-email-holger@freyther.de> <1404976392-22876-2-git-send-email-holger@freyther.de> <20140710120343.32448.qmail@stuge.se> Message-ID: <20140710184605.GL22956@xiaoyu.lan> On Thu, Jul 10, 2014 at 02:03:43PM +0200, Peter Stuge wrote: > > + /* > > + * Check if this could be a T7L9V tag. Do it by > > + * shifting it to the right once. Note that this > > + * means that mixing T7L9V with other tags is not > > + * possible. > > Why not explicitly specify to do this test for each tag? I am not sure if I follow. Do you propose to iterate over the definition list and check which tags fits best and if it should be shifted or not? > Ie. leave the old function as-is, add a new function with the T7L9V > heuristic, and use the new function only at call sites where T7L9V > may actually be encountered. Yes, I have considered this option too. We could introduce a tlv_parser variant that specifies which routine to use for a single tag. holger From mailman-bounces at lists.osmocom.org Sun Jul 13 07:00:06 2014 From: mailman-bounces at lists.osmocom.org (mailman-bounces at lists.osmocom.org) Date: Sun, 13 Jul 2014 09:00:06 +0200 Subject: OpenBSC unsubscribe notification Message-ID: mki at mki-consult.de has been removed from OpenBSC. From alexander.chemeris at gmail.com Wed Jul 16 00:46:44 2014 From: alexander.chemeris at gmail.com (Alexander Chemeris) Date: Tue, 15 Jul 2014 20:46:44 -0400 Subject: TRX Clock calibration In-Reply-To: <53C5C48C.9050900@gmail.com> References: <53C5C48C.9050900@gmail.com> Message-ID: Choukoumoun, The question is related to the osmo-trx more than to UmTRX, so I'm moving it to the Osmocom mailing list: On Tue, Jul 15, 2014 at 8:17 PM, choukoumoun wrote: > Hello guys. > > I have a UMTRX my UHD/OPENBTS or UHD/OSMO-TRX same working fine but wen i > start osmo-trx and openbts i have this error Could you specify where did you get sources and which exact versions and commit numbers do you use? Did you try to use osmo-trx with Osmocom software rather than with OpenBTS? > Osmo-trx : > > linux; GNU C++ version 4.8.1; Boost_105300; UHD_003.004.000-4fa97a1 > > Config Settings > Log Level............... NOTICE > Device args............. addr=192.168.10.2 > TRX Base Port........... 5700 > TRX Address............. 127.0.0.1 > Channels................ 1 > Samples-per-Symbol...... 4 > External Reference...... Disabled > C0 Filler Table......... Disabled > Diversity............... Disabled > Tuning offset........... 0 > > -- Opening a UmTRX device... > -- Current recv frame size: 1472 bytes > -- Current send frame size: 1472 bytes > -- Setting UmTRX 4 SPS > -- Transceiver active with 1 channel(s) > > ALERT 139940970051328 02:13:33.7 UHDDevice.cpp:993:writeSamples: UHD: Device > send timed out > "Constantely" ..... > > > anybody have a idea ? > > > my usrp probe out : > > linux; GNU C++ version 4.8.1; Boost_105300; UHD_003.004.000-4fa97a1 > > -- Opening a UmTRX device... > -- Current recv frame size: 1472 bytes > -- Current send frame size: 1472 bytes > _____________________________________________________ > / > | Device: UmTRX Device > | _____________________________________________________ > | / > | | Mboard: UMTRX-REV0 > | | hardware: 64000 > | | mac-addr: 00:50:c2:85:3f:ff > | | ip-addr: 192.168.10.2 > | | gpsdo: none > | | serial: 7 > | | name: UmTRX > | | tcxo-dac: 2048 > | | > | | Time sources: none, external, _external_, mimo > | | Clock sources: internal, external, mimo > | | Sensors: ref_locked > | | _____________________________________________________ > | | / > | | | RX DSP: 0 > | | | Freq range: -6.500 to 6.500 Mhz > | | _____________________________________________________ > | | / > | | | RX DSP: 1 > | | | Freq range: -6.500 to 6.500 Mhz > | | _____________________________________________________ > | | / > | | | RX Dboard: A > | | | ID: LMS6002D (0xfa07) > | | | Serial: 7.A > | | | _____________________________________________________ > | | | / > | | | | RX Subdev: 0 > | | | | Name: LMS6002D (0xfa07) - 0 > | | | | Antennas: RX0, RX1, RX2, RX3, CAL > | | | | Sensors: lo_locked > | | | | Freq range: 232.500 to 3720.000 Mhz > | | | | Gain range VGA1: 0.0 to 126.0 step 1.0 dB > | | | | Gain range VGA2: 0.0 to 30.0 step 3.0 dB > | | | | Connection Type: IQ > | | | | Uses LO offset: No > | | | _____________________________________________________ > | | | / > | | | | RX Codec: A > | | | | Name: LMS_RX > | | | | Gain Elements: None > | | _____________________________________________________ > | | / > | | | RX Dboard: B > | | | ID: LMS6002D (0xfa07) > | | | Serial: 7.B > | | | _____________________________________________________ > | | | / > | | | | RX Subdev: 0 > | | | | Name: LMS6002D (0xfa07) - 0 > | | | | Antennas: RX0, RX1, RX2, RX3, CAL > | | | | Sensors: lo_locked > | | | | Freq range: 232.500 to 3720.000 Mhz > | | | | Gain range VGA1: 0.0 to 126.0 step 1.0 dB > | | | | Gain range VGA2: 0.0 to 30.0 step 3.0 dB > | | | | Connection Type: IQ > | | | | Uses LO offset: No > | | | _____________________________________________________ > | | | / > | | | | RX Codec: B > | | | | Name: LMS_RX > | | | | Gain Elements: None > | | _____________________________________________________ > | | / > | | | TX DSP: 0 > | | | Freq range: -6.500 to 6.500 Mhz > | | _____________________________________________________ > | | / > | | | TX DSP: 1 > | | | Freq range: -6.500 to 6.500 Mhz > | | _____________________________________________________ > | | / > | | | TX Dboard: A > | | | ID: LMS6002D (0xfa09) > | | | Serial: 7.A > | | | _____________________________________________________ > | | | / > | | | | TX Subdev: 0 > | | | | Name: LMS6002D (0xfa09) - 0 > | | | | Antennas: TX0, TX1, TX2, CAL > | | | | Sensors: lo_locked > | | | | Freq range: 232.500 to 3720.000 Mhz > | | | | Gain range VGA1: -35.0 to -4.0 step 1.0 dB > | | | | Gain range VGA2: 0.0 to 25.0 step 1.0 dB > | | | | Connection Type: IQ > | | | | Uses LO offset: No > | | | _____________________________________________________ > | | | / > | | | | TX Codec: A > | | | | Name: LMS_TX > | | | | Gain Elements: None > | | _____________________________________________________ > | | / > | | | TX Dboard: B > | | | ID: LMS6002D (0xfa09) > | | | Serial: 7.B > | | | _____________________________________________________ > | | | / > | | | | TX Subdev: 0 > | | | | Name: LMS6002D (0xfa09) - 0 > | | | | Antennas: TX0, TX1, TX2, CAL > | | | | Sensors: lo_locked > | | | | Freq range: 232.500 to 3720.000 Mhz > | | | | Gain range VGA1: -35.0 to -4.0 step 1.0 dB > | | | | Gain range VGA2: 0.0 to 25.0 step 1.0 dB > | | | | Connection Type: IQ > | | | | Uses LO offset: No > | | | _____________________________________________________ > | | | / > | | | | TX Codec: B > | | | | Name: LMS_TX > | | | | Gain Elements: None > > > I make the VCXO configuration procedure with the GPS but no success... The issue with "UHD: Device send timed out" have nothing to do with the VCXO calibration. The issue is because of a issue in communication between the host system and the UmTRX. What is your hardware setup? Particularly: - Do you use a switch between the UmTRX and the host system? - Do you run it on a real hardware or in a VM? - Is your host system powerful enough? -- Regards, Alexander Chemeris. CEO, Fairwaves, Inc. https://fairwaves.co From choukoumoun at gmail.com Wed Jul 16 00:53:30 2014 From: choukoumoun at gmail.com (choukoumoun) Date: Wed, 16 Jul 2014 02:53:30 +0200 Subject: TRX Clock calibration In-Reply-To: <53C5CCD1.9000201@gmail.com> References: <53C5CCD1.9000201@gmail.com> Message-ID: <53C5CD0A.6050809@gmail.com> -------- Message original -------- Sujet: Re: TRX Clock calibration Date : Wed, 16 Jul 2014 02:52:33 +0200 De : choukoumoun Pour : Alexander Chemeris Le 16/07/2014 02:46, Alexander Chemeris a ?crit : > Choukoumoun, > > The question is related to the osmo-trx more than to UmTRX, so I'm > moving it to the Osmocom mailing list: > > On Tue, Jul 15, 2014 at 8:17 PM, choukoumoun wrote: >> Hello guys. >> >> I have a UMTRX my UHD/OPENBTS or UHD/OSMO-TRX same working fine but wen i >> start osmo-trx and openbts i have this error > Could you specify where did you get sources and which exact versions > and commit numbers do you use? > > Did you try to use osmo-trx with Osmocom software rather than with OpenBTS? > >> Osmo-trx : >> >> linux; GNU C++ version 4.8.1; Boost_105300; UHD_003.004.000-4fa97a1 >> >> Config Settings >> Log Level............... NOTICE >> Device args............. addr=192.168.10.2 >> TRX Base Port........... 5700 >> TRX Address............. 127.0.0.1 >> Channels................ 1 >> Samples-per-Symbol...... 4 >> External Reference...... Disabled >> C0 Filler Table......... Disabled >> Diversity............... Disabled >> Tuning offset........... 0 >> >> -- Opening a UmTRX device... >> -- Current recv frame size: 1472 bytes >> -- Current send frame size: 1472 bytes >> -- Setting UmTRX 4 SPS >> -- Transceiver active with 1 channel(s) >> >> ALERT 139940970051328 02:13:33.7 UHDDevice.cpp:993:writeSamples: UHD: Device >> send timed out >> "Constantely" ..... >> >> >> anybody have a idea ? >> >> >> my usrp probe out : >> >> linux; GNU C++ version 4.8.1; Boost_105300; UHD_003.004.000-4fa97a1 >> >> -- Opening a UmTRX device... >> -- Current recv frame size: 1472 bytes >> -- Current send frame size: 1472 bytes >> _____________________________________________________ >> / >> | Device: UmTRX Device >> | _____________________________________________________ >> | / >> | | Mboard: UMTRX-REV0 >> | | hardware: 64000 >> | | mac-addr: 00:50:c2:85:3f:ff >> | | ip-addr: 192.168.10.2 >> | | gpsdo: none >> | | serial: 7 >> | | name: UmTRX >> | | tcxo-dac: 2048 >> | | >> | | Time sources: none, external, _external_, mimo >> | | Clock sources: internal, external, mimo >> | | Sensors: ref_locked >> | | _____________________________________________________ >> | | / >> | | | RX DSP: 0 >> | | | Freq range: -6.500 to 6.500 Mhz >> | | _____________________________________________________ >> | | / >> | | | RX DSP: 1 >> | | | Freq range: -6.500 to 6.500 Mhz >> | | _____________________________________________________ >> | | / >> | | | RX Dboard: A >> | | | ID: LMS6002D (0xfa07) >> | | | Serial: 7.A >> | | | _____________________________________________________ >> | | | / >> | | | | RX Subdev: 0 >> | | | | Name: LMS6002D (0xfa07) - 0 >> | | | | Antennas: RX0, RX1, RX2, RX3, CAL >> | | | | Sensors: lo_locked >> | | | | Freq range: 232.500 to 3720.000 Mhz >> | | | | Gain range VGA1: 0.0 to 126.0 step 1.0 dB >> | | | | Gain range VGA2: 0.0 to 30.0 step 3.0 dB >> | | | | Connection Type: IQ >> | | | | Uses LO offset: No >> | | | _____________________________________________________ >> | | | / >> | | | | RX Codec: A >> | | | | Name: LMS_RX >> | | | | Gain Elements: None >> | | _____________________________________________________ >> | | / >> | | | RX Dboard: B >> | | | ID: LMS6002D (0xfa07) >> | | | Serial: 7.B >> | | | _____________________________________________________ >> | | | / >> | | | | RX Subdev: 0 >> | | | | Name: LMS6002D (0xfa07) - 0 >> | | | | Antennas: RX0, RX1, RX2, RX3, CAL >> | | | | Sensors: lo_locked >> | | | | Freq range: 232.500 to 3720.000 Mhz >> | | | | Gain range VGA1: 0.0 to 126.0 step 1.0 dB >> | | | | Gain range VGA2: 0.0 to 30.0 step 3.0 dB >> | | | | Connection Type: IQ >> | | | | Uses LO offset: No >> | | | _____________________________________________________ >> | | | / >> | | | | RX Codec: B >> | | | | Name: LMS_RX >> | | | | Gain Elements: None >> | | _____________________________________________________ >> | | / >> | | | TX DSP: 0 >> | | | Freq range: -6.500 to 6.500 Mhz >> | | _____________________________________________________ >> | | / >> | | | TX DSP: 1 >> | | | Freq range: -6.500 to 6.500 Mhz >> | | _____________________________________________________ >> | | / >> | | | TX Dboard: A >> | | | ID: LMS6002D (0xfa09) >> | | | Serial: 7.A >> | | | _____________________________________________________ >> | | | / >> | | | | TX Subdev: 0 >> | | | | Name: LMS6002D (0xfa09) - 0 >> | | | | Antennas: TX0, TX1, TX2, CAL >> | | | | Sensors: lo_locked >> | | | | Freq range: 232.500 to 3720.000 Mhz >> | | | | Gain range VGA1: -35.0 to -4.0 step 1.0 dB >> | | | | Gain range VGA2: 0.0 to 25.0 step 1.0 dB >> | | | | Connection Type: IQ >> | | | | Uses LO offset: No >> | | | _____________________________________________________ >> | | | / >> | | | | TX Codec: A >> | | | | Name: LMS_TX >> | | | | Gain Elements: None >> | | _____________________________________________________ >> | | / >> | | | TX Dboard: B >> | | | ID: LMS6002D (0xfa09) >> | | | Serial: 7.B >> | | | _____________________________________________________ >> | | | / >> | | | | TX Subdev: 0 >> | | | | Name: LMS6002D (0xfa09) - 0 >> | | | | Antennas: TX0, TX1, TX2, CAL >> | | | | Sensors: lo_locked >> | | | | Freq range: 232.500 to 3720.000 Mhz >> | | | | Gain range VGA1: -35.0 to -4.0 step 1.0 dB >> | | | | Gain range VGA2: 0.0 to 25.0 step 1.0 dB >> | | | | Connection Type: IQ >> | | | | Uses LO offset: No >> | | | _____________________________________________________ >> | | | / >> | | | | TX Codec: B >> | | | | Name: LMS_TX >> | | | | Gain Elements: None >> >> >> I make the VCXO configuration procedure with the GPS but no success... > The issue with "UHD: Device send timed out" have nothing to do with > the VCXO calibration. The issue is because of a issue in communication > between the host system and the UmTRX. > > What is your hardware setup? Particularly: > - Do you use a switch between the UmTRX and the host system? Nop my laptop is connected directly of the umtrx > - Do you run it on a real hardware or in a VM? real ubuntu 13.04 64 bits > - Is your host system powerful enough? Intel Core I5, 8Gb ram > -------------- next part -------------- An HTML attachment was scrubbed... URL: From alexander.chemeris at gmail.com Wed Jul 16 01:09:51 2014 From: alexander.chemeris at gmail.com (Alexander Chemeris) Date: Tue, 15 Jul 2014 21:09:51 -0400 Subject: TRX Clock calibration In-Reply-To: <53C5CD0A.6050809@gmail.com> References: <53C5CCD1.9000201@gmail.com> <53C5CD0A.6050809@gmail.com> Message-ID: choukoumoun, Please answer these questions before we could look into the issue: > >> I have a UMTRX my UHD/OPENBTS or UHD/OSMO-TRX same working fine but wen i > >> start osmo-trx and openbts i have this error > > Could you specify where did you get sources and which exact versions > > and commit numbers do you use? > > > > Did you try to use osmo-trx with Osmocom software rather than with OpenBTS? -- Regards, Alexander Chemeris. CEO, Fairwaves, Inc. https://fairwaves.co From choukoumoun at gmail.com Wed Jul 16 09:51:20 2014 From: choukoumoun at gmail.com (choukoumoun) Date: Wed, 16 Jul 2014 11:51:20 +0200 Subject: TRX Clock calibration In-Reply-To: References: <53C5CCD1.9000201@gmail.com> <53C5CD0A.6050809@gmail.com> Message-ID: <53C64B18.9010901@gmail.com> Le 16/07/2014 03:09, Alexander Chemeris a ?crit : > choukoumoun, > > Please answer these questions before we could look into the issue: > >>>> I have a UMTRX my UHD/OPENBTS or UHD/OSMO-TRX same working fine but wen i >>>> start osmo-trx and openbts i have this error >>> Could you specify where did you get sources and which exact versions >>> and commit numbers do you use? Where can i get the commit number in my installation ? >>> >>> Did you try to use osmo-trx with Osmocom software rather than with OpenBTS? Yes im trying osmo-trx with osmo-bts and openbsc and i have the same error. > > -------------- next part -------------- An HTML attachment was scrubbed... URL: From choukoumoun at gmail.com Thu Jul 24 01:07:39 2014 From: choukoumoun at gmail.com (choukoumoun) Date: Thu, 24 Jul 2014 03:07:39 +0200 Subject: TRX Clock calibration In-Reply-To: <53C64B18.9010901@gmail.com> References: <53C5CCD1.9000201@gmail.com> <53C5CD0A.6050809@gmail.com> <53C64B18.9010901@gmail.com> Message-ID: <53D05C5B.8050005@gmail.com> Hello, Im using Building version: 003.004.000-30f4376 Thanks. Le 16/07/2014 11:51, choukoumoun a ?crit : > > Le 16/07/2014 03:09, Alexander Chemeris a ?crit : >> choukoumoun, >> >> Please answer these questions before we could look into the issue: >> >>>>> I have a UMTRX my UHD/OPENBTS or UHD/OSMO-TRX same working fine but wen i >>>>> start osmo-trx and openbts i have this error >>>> Could you specify where did you get sources and which exact versions >>>> and commit numbers do you use? > Where can i get the commit number in my installation ? >>>> Did you try to use osmo-trx with Osmocom software rather than with OpenBTS? > Yes im trying osmo-trx with osmo-bts and openbsc and i have the same > error. >> >> > -------------- next part -------------- An HTML attachment was scrubbed... URL: From ralph at schmid.xxx Wed Jul 16 06:13:07 2014 From: ralph at schmid.xxx (Ralph A. Schmid, dk5ras) Date: Wed, 16 Jul 2014 08:13:07 +0200 Subject: osmo-trx with RAD1? Message-ID: <012001cfa0bd$03847830$0a8d6890$@schmid.xxx> Hi, When having a look at http://discourse.criticalengineering.org/t/howto-gsm-base-station-with-the-b eaglebone-black-debian-gnu-linux-and-a-usrp/56 I wonder if there is a way to use the osmo-trx with rangenetworks RAD1/SDR1 radio. I do not yet own an Ettus B210, so it would be fun using the BeagleBone with the RAD1/SDR1, what is some shrinked and at the same time extended USRP1 radio. Ralph. -- Ralph A. Schmid Mondstr. 10 90762 F?rth +49-171-3631223 ralph at schmid.xxx http://www.bclog.de/ From peter at stuge.se Wed Jul 16 14:05:01 2014 From: peter at stuge.se (Peter Stuge) Date: Wed, 16 Jul 2014 16:05:01 +0200 Subject: osmo-trx with RAD1? In-Reply-To: <012001cfa0bd$03847830$0a8d6890$@schmid.xxx> References: <012001cfa0bd$03847830$0a8d6890$@schmid.xxx> Message-ID: <20140716140501.13881.qmail@stuge.se> Ralph A. Schmid, dk5ras wrote: > I wonder if there is a way to use the osmo-trx with rangenetworks RAD1/SDR1 > radio. Try it and let us know how it goes? //Peter From tom at tsou.cc Wed Jul 16 17:38:55 2014 From: tom at tsou.cc (Tom Tsou) Date: Wed, 16 Jul 2014 13:38:55 -0400 Subject: osmo-trx with RAD1? In-Reply-To: <012001cfa0bd$03847830$0a8d6890$@schmid.xxx> References: <012001cfa0bd$03847830$0a8d6890$@schmid.xxx> Message-ID: On Wed, Jul 16, 2014 at 2:13 AM, Ralph A. Schmid, dk5ras wrote: > When having a look at > http://discourse.criticalengineering.org/t/howto-gsm-base-station-with-the-b > eaglebone-black-debian-gnu-linux-and-a-usrp/56 > I wonder if there is a way to use the osmo-trx with rangenetworks RAD1/SDR1 > radio. I do not yet own an Ettus B210, so it would be fun using the > BeagleBone with the RAD1/SDR1, what is some shrinked and at the same time > extended USRP1 radio. You would need to use the RAD1 transceiver. The socket API of osmo-trx is identical to that of the RAD1 host code, but the internal implementation has clearly diverged. I would not expect to see RAD1 support in osmo-trx anytime soon. -TT From alexander.chemeris at gmail.com Wed Jul 16 17:54:59 2014 From: alexander.chemeris at gmail.com (Alexander Chemeris) Date: Wed, 16 Jul 2014 13:54:59 -0400 Subject: osmo-trx with RAD1? In-Reply-To: References: <012001cfa0bd$03847830$0a8d6890$@schmid.xxx> Message-ID: On Jul 16, 2014 1:40 PM, "Tom Tsou" wrote: > > On Wed, Jul 16, 2014 at 2:13 AM, Ralph A. Schmid, dk5ras > wrote: > > When having a look at > > http://discourse.criticalengineering.org/t/howto-gsm-base-station-with-the-b > > eaglebone-black-debian-gnu-linux-and-a-usrp/56 > > I wonder if there is a way to use the osmo-trx with rangenetworks RAD1/SDR1 > > radio. I do not yet own an Ettus B210, so it would be fun using the > > BeagleBone with the RAD1/SDR1, what is some shrinked and at the same time > > extended USRP1 radio. > > You would need to use the RAD1 transceiver. The socket API of osmo-trx > is identical to that of the RAD1 host code, but the internal > implementation has clearly diverged. I would not expect to see RAD1 > support in osmo-trx anytime soon. That is unless someone volunteers to add this support. Please excuse typos. Written with a touchscreen keyboard. -- Regards, Alexander Chemeris CEO Fairwaves, Inc. https://fairwaves.co -------------- next part -------------- An HTML attachment was scrubbed... URL: From kheimerl at cs.berkeley.edu Wed Jul 16 18:03:46 2014 From: kheimerl at cs.berkeley.edu (Kurtis Heimerl) Date: Wed, 16 Jul 2014 11:03:46 -0700 Subject: osmo-trx with RAD1? In-Reply-To: References: <012001cfa0bd$03847830$0a8d6890$@schmid.xxx> Message-ID: We at Berkeley tried this a few months ago (Range was kind enough to help us fab RAD1s in support for a Filipino project). Made some progress, but we never got it working. So it definitely doesn't work out of the box. On Wed, Jul 16, 2014 at 10:54 AM, Alexander Chemeris < alexander.chemeris at gmail.com> wrote: > > On Jul 16, 2014 1:40 PM, "Tom Tsou" wrote: > > > > On Wed, Jul 16, 2014 at 2:13 AM, Ralph A. Schmid, dk5ras > > wrote: > > > When having a look at > > > > http://discourse.criticalengineering.org/t/howto-gsm-base-station-with-the-b > > > eaglebone-black-debian-gnu-linux-and-a-usrp/56 > > > I wonder if there is a way to use the osmo-trx with rangenetworks > RAD1/SDR1 > > > radio. I do not yet own an Ettus B210, so it would be fun using the > > > BeagleBone with the RAD1/SDR1, what is some shrinked and at the same > time > > > extended USRP1 radio. > > > > You would need to use the RAD1 transceiver. The socket API of osmo-trx > > is identical to that of the RAD1 host code, but the internal > > implementation has clearly diverged. I would not expect to see RAD1 > > support in osmo-trx anytime soon. > > That is unless someone volunteers to add this support. > > Please excuse typos. Written with a touchscreen keyboard. > > -- > Regards, > Alexander Chemeris > CEO Fairwaves, Inc. > https://fairwaves.co > -------------- next part -------------- An HTML attachment was scrubbed... URL: From tom at tsou.cc Wed Jul 16 18:13:05 2014 From: tom at tsou.cc (Tom Tsou) Date: Wed, 16 Jul 2014 14:13:05 -0400 Subject: osmo-trx with RAD1? In-Reply-To: References: <012001cfa0bd$03847830$0a8d6890$@schmid.xxx> Message-ID: Hi Kurtis, On Wed, Jul 16, 2014 at 2:03 PM, Kurtis Heimerl wrote: > We at Berkeley tried this a few months ago (Range was kind enough to help us > fab RAD1s in support for a Filipino project). Made some progress, but we > never got it working. So it definitely doesn't work out of the box. Can you clarify what was tried? Are we talking about TransceiverRAD1 with Osmocom stack? OpenBTS-RAD1 on Beagleboard? RAD1 with OsmoTRX? or something else? -TT From kheimerl at cs.berkeley.edu Wed Jul 16 18:14:29 2014 From: kheimerl at cs.berkeley.edu (Kurtis Heimerl) Date: Wed, 16 Jul 2014 11:14:29 -0700 Subject: osmo-trx with RAD1? In-Reply-To: References: <012001cfa0bd$03847830$0a8d6890$@schmid.xxx> Message-ID: RAD1, using modified TransceiverRAD1, with OsmoTRX. On Wed, Jul 16, 2014 at 11:13 AM, Tom Tsou wrote: > Hi Kurtis, > > On Wed, Jul 16, 2014 at 2:03 PM, Kurtis Heimerl > wrote: > > We at Berkeley tried this a few months ago (Range was kind enough to > help us > > fab RAD1s in support for a Filipino project). Made some progress, but we > > never got it working. So it definitely doesn't work out of the box. > > Can you clarify what was tried? > > Are we talking about TransceiverRAD1 with Osmocom stack? OpenBTS-RAD1 > on Beagleboard? RAD1 with OsmoTRX? or something else? > > -TT > -------------- next part -------------- An HTML attachment was scrubbed... URL: From kheimerl at cs.berkeley.edu Wed Jul 16 18:15:26 2014 From: kheimerl at cs.berkeley.edu (Kurtis Heimerl) Date: Wed, 16 Jul 2014 11:15:26 -0700 Subject: osmo-trx with RAD1? In-Reply-To: References: <012001cfa0bd$03847830$0a8d6890$@schmid.xxx> Message-ID: To be clear, I think it was a tractable problem, our use case for it just fell through. I'd be happy to share what it took to build and run (I think I saw beacon but couldn't receive) but I can't seem to find the repo right now... On Wed, Jul 16, 2014 at 11:14 AM, Kurtis Heimerl wrote: > RAD1, using modified TransceiverRAD1, with OsmoTRX. > > > On Wed, Jul 16, 2014 at 11:13 AM, Tom Tsou wrote: > >> Hi Kurtis, >> >> On Wed, Jul 16, 2014 at 2:03 PM, Kurtis Heimerl >> wrote: >> > We at Berkeley tried this a few months ago (Range was kind enough to >> help us >> > fab RAD1s in support for a Filipino project). Made some progress, but we >> > never got it working. So it definitely doesn't work out of the box. >> >> Can you clarify what was tried? >> >> Are we talking about TransceiverRAD1 with Osmocom stack? OpenBTS-RAD1 >> on Beagleboard? RAD1 with OsmoTRX? or something else? >> >> -TT >> > > -------------- next part -------------- An HTML attachment was scrubbed... URL: From tom at tsou.cc Wed Jul 16 18:27:52 2014 From: tom at tsou.cc (Tom Tsou) Date: Wed, 16 Jul 2014 14:27:52 -0400 Subject: osmo-trx with RAD1? In-Reply-To: References: <012001cfa0bd$03847830$0a8d6890$@schmid.xxx> Message-ID: On Wed, Jul 16, 2014 at 2:14 PM, Kurtis Heimerl wrote: > RAD1, using modified TransceiverRAD1, with OsmoTRX. Since OsmoTRX and TransceiverRAD1 serve the same role, I assume you mean TransceiverRAD1 with osmo-bts-trx. That said, the current module naming not exactly the most intuitive. -TT From kheimerl at cs.berkeley.edu Wed Jul 16 18:30:13 2014 From: kheimerl at cs.berkeley.edu (Kurtis Heimerl) Date: Wed, 16 Jul 2014 11:30:13 -0700 Subject: osmo-trx with RAD1? In-Reply-To: References: <012001cfa0bd$03847830$0a8d6890$@schmid.xxx> Message-ID: Yes! That's exactly what I mean. Sorry about that. On Wed, Jul 16, 2014 at 11:27 AM, Tom Tsou wrote: > On Wed, Jul 16, 2014 at 2:14 PM, Kurtis Heimerl > wrote: > > RAD1, using modified TransceiverRAD1, with OsmoTRX. > > Since OsmoTRX and TransceiverRAD1 serve the same role, I assume you > mean TransceiverRAD1 with osmo-bts-trx. > > That said, the current module naming not exactly the most intuitive. > > -TT > -------------- next part -------------- An HTML attachment was scrubbed... URL: From dwillmann at sysmocom.de Wed Jul 16 17:04:28 2014 From: dwillmann at sysmocom.de (Daniel Willmann) Date: Wed, 16 Jul 2014 19:04:28 +0200 Subject: [osmo-pcu 1/5] bts: Ensure tbf direction with OSMO_ASSERT() Message-ID: <2207c5e4ef0565ab782196a80cc45dcc458938e4.1405530272.git.daniel@totalueberwachung.de> In the lookup functions make sure that we are actually returning tbfs with the expected direction. Ticket: SYS#389 Sponsored-by: On-Waves ehf --- src/bts.cpp | 22 ++++++++++++++++------ src/bts.h | 3 ++- 2 files changed, 18 insertions(+), 7 deletions(-) diff --git a/src/bts.cpp b/src/bts.cpp index 08baee0..f614dab 100644 --- a/src/bts.cpp +++ b/src/bts.cpp @@ -234,12 +234,14 @@ gprs_rlcmac_tbf *BTS::tbf_by_tlli(uint32_t tlli, enum gprs_rlcmac_tbf_direction struct gprs_rlcmac_tbf *tbf; if (dir == GPRS_RLCMAC_UL_TBF) { llist_for_each_entry(tbf, &m_bts.ul_tbfs, list) { + OSMO_ASSERT(tbf->direction == dir); if (tbf->state_is_not(GPRS_RLCMAC_RELEASING) && tbf->tlli() == tlli && tbf->is_tlli_valid()) return tbf; } } else { llist_for_each_entry(tbf, &m_bts.dl_tbfs, list) { + OSMO_ASSERT(tbf->direction == dir); if (tbf->state_is_not(GPRS_RLCMAC_RELEASING) && tbf->tlli() == tlli) return tbf; @@ -258,8 +260,10 @@ gprs_rlcmac_tbf *BTS::dl_tbf_by_poll_fn(uint32_t fn, uint8_t trx, uint8_t ts) if (tbf->state_is_not(GPRS_RLCMAC_RELEASING) && tbf->poll_state == GPRS_RLCMAC_POLL_SCHED && tbf->poll_fn == fn && tbf->trx->trx_no == trx - && tbf->control_ts == ts) + && tbf->control_ts == ts) { + OSMO_ASSERT(tbf->direction == GPRS_RLCMAC_DL_TBF); return tbf; + } } return NULL; } @@ -273,8 +277,10 @@ gprs_rlcmac_tbf *BTS::ul_tbf_by_poll_fn(uint32_t fn, uint8_t trx, uint8_t ts) if (tbf->state_is_not(GPRS_RLCMAC_RELEASING) && tbf->poll_state == GPRS_RLCMAC_POLL_SCHED && tbf->poll_fn == fn && tbf->trx->trx_no == trx - && tbf->control_ts == ts) + && tbf->control_ts == ts) { + OSMO_ASSERT(tbf->direction == GPRS_RLCMAC_UL_TBF); return tbf; + } } return NULL; } @@ -307,8 +313,10 @@ gprs_rlcmac_tbf *BTS::tbf_by_tfi(uint8_t tfi, uint8_t trx, if (!tbf) return NULL; - if (tbf->state_is_not(GPRS_RLCMAC_RELEASING)) + if (tbf->state_is_not(GPRS_RLCMAC_RELEASING)) { + OSMO_ASSERT(tbf->direction == dir); return tbf; + } return NULL; } @@ -1023,11 +1031,13 @@ int gprs_rlcmac_pdch::rcv_block(uint8_t *data, uint8_t len, uint32_t fn, int8_t return rc; } -gprs_rlcmac_tbf *gprs_rlcmac_pdch::tbf_from_list_by_tfi(struct llist_head *tbf_list, uint8_t tfi) +gprs_rlcmac_tbf *gprs_rlcmac_pdch::tbf_from_list_by_tfi(struct llist_head *tbf_list, uint8_t tfi, + enum gprs_rlcmac_tbf_direction dir) { gprs_rlcmac_tbf *tbf; llist_for_each_entry(tbf, tbf_list, list) { + OSMO_ASSERT(tbf->direction == dir); if (tbf->tfi() != tfi) continue; if (!tbf->pdch[ts_no]) @@ -1039,10 +1049,10 @@ gprs_rlcmac_tbf *gprs_rlcmac_pdch::tbf_from_list_by_tfi(struct llist_head *tbf_l gprs_rlcmac_tbf *gprs_rlcmac_pdch::ul_tbf_by_tfi(uint8_t tfi) { - return tbf_from_list_by_tfi(&bts_data()->ul_tbfs, tfi); + return tbf_from_list_by_tfi(&bts_data()->ul_tbfs, tfi, GPRS_RLCMAC_UL_TBF); } gprs_rlcmac_tbf *gprs_rlcmac_pdch::dl_tbf_by_tfi(uint8_t tfi) { - return tbf_from_list_by_tfi(&bts_data()->dl_tbfs, tfi); + return tbf_from_list_by_tfi(&bts_data()->dl_tbfs, tfi, GPRS_RLCMAC_DL_TBF); } diff --git a/src/bts.h b/src/bts.h index 621bcba..a0b808e 100644 --- a/src/bts.h +++ b/src/bts.h @@ -87,7 +87,8 @@ private: void rcv_control_dl_ack_nack(Packet_Downlink_Ack_Nack_t *, uint32_t fn); void rcv_resource_request(Packet_Resource_Request_t *t, uint32_t fn); void rcv_measurement_report(Packet_Measurement_Report_t *t, uint32_t fn); - gprs_rlcmac_tbf *tbf_from_list_by_tfi(struct llist_head *tbf_list, uint8_t tfi); + gprs_rlcmac_tbf *tbf_from_list_by_tfi(struct llist_head *tbf_list, uint8_t tfi, + enum gprs_rlcmac_tbf_direction dir); #endif }; -- 1.8.4.2 From dwillmann at sysmocom.de Wed Jul 16 17:04:29 2014 From: dwillmann at sysmocom.de (Daniel Willmann) Date: Wed, 16 Jul 2014 19:04:29 +0200 Subject: [osmo-pcu 2/5] tbf: Add ul and dl TBF types and allocate them in tbf_alloc() In-Reply-To: <2207c5e4ef0565ab782196a80cc45dcc458938e4.1405530272.git.daniel@totalueberwachung.de> References: <2207c5e4ef0565ab782196a80cc45dcc458938e4.1405530272.git.daniel@totalueberwachung.de> Message-ID: <078bb713e1f00b0f2d045baa7fd4e0eb254cdf29.1405530272.git.daniel@totalueberwachung.de> Ticket: SYS#389 Sponsored-by: On-Waves ehf --- src/tbf.cpp | 6 +++++- src/tbf.h | 6 ++++++ 2 files changed, 11 insertions(+), 1 deletion(-) diff --git a/src/tbf.cpp b/src/tbf.cpp index f913f97..39549f1 100644 --- a/src/tbf.cpp +++ b/src/tbf.cpp @@ -495,7 +495,11 @@ struct gprs_rlcmac_tbf *tbf_alloc(struct gprs_rlcmac_bts *bts, if (trx >= 8 || tfi >= 32) return NULL; - tbf = talloc_zero(tall_pcu_ctx, struct gprs_rlcmac_tbf); + if (dir == GPRS_RLCMAC_UL_TBF) + tbf = talloc_zero(tall_pcu_ctx, struct gprs_rlcmac_ul_tbf); + else + tbf = talloc_zero(tall_pcu_ctx, struct gprs_rlcmac_dl_tbf); + if (!tbf) return NULL; diff --git a/src/tbf.h b/src/tbf.h index 80e2068..8464e19 100644 --- a/src/tbf.h +++ b/src/tbf.h @@ -326,6 +326,12 @@ inline time_t gprs_rlcmac_tbf::created_ts() const return m_created_ts; } +struct gprs_rlcmac_dl_tbf : public gprs_rlcmac_tbf { +}; + +struct gprs_rlcmac_ul_tbf : public gprs_rlcmac_tbf { +}; + #endif #ifdef __cplusplus -- 1.8.4.2 From dwillmann at sysmocom.de Wed Jul 16 17:04:30 2014 From: dwillmann at sysmocom.de (Daniel Willmann) Date: Wed, 16 Jul 2014 19:04:30 +0200 Subject: [osmo-pcu 3/5] bts: Return the special type for {ul, dl}_tbf_by_* functions In-Reply-To: <2207c5e4ef0565ab782196a80cc45dcc458938e4.1405530272.git.daniel@totalueberwachung.de> References: <2207c5e4ef0565ab782196a80cc45dcc458938e4.1405530272.git.daniel@totalueberwachung.de> Message-ID: Start returning the special type instead of the base gprs_rlcmac_tbf when retrieving a TBF. Ticket: SYS#389 Sponsored-by: On-Waves ehf --- src/bts.cpp | 36 ++++++++++++++++++------------------ src/bts.h | 16 ++++++++-------- 2 files changed, 26 insertions(+), 26 deletions(-) diff --git a/src/bts.cpp b/src/bts.cpp index f614dab..68d72f2 100644 --- a/src/bts.cpp +++ b/src/bts.cpp @@ -217,15 +217,15 @@ int BTS::add_paging(uint8_t chan_needed, uint8_t *identity_lv) } /* search for active downlink tbf */ -gprs_rlcmac_tbf *BTS::dl_tbf_by_tlli(uint32_t tlli) +gprs_rlcmac_dl_tbf *BTS::dl_tbf_by_tlli(uint32_t tlli) { - return tbf_by_tlli(tlli, GPRS_RLCMAC_DL_TBF); + return (gprs_rlcmac_dl_tbf *)tbf_by_tlli(tlli, GPRS_RLCMAC_DL_TBF); } /* search for active uplink tbf */ -gprs_rlcmac_tbf *BTS::ul_tbf_by_tlli(uint32_t tlli) +gprs_rlcmac_ul_tbf *BTS::ul_tbf_by_tlli(uint32_t tlli) { - return tbf_by_tlli(tlli, GPRS_RLCMAC_UL_TBF); + return (gprs_rlcmac_ul_tbf *)tbf_by_tlli(tlli, GPRS_RLCMAC_UL_TBF); } /* search for active downlink or uplink tbf */ @@ -250,9 +250,9 @@ gprs_rlcmac_tbf *BTS::tbf_by_tlli(uint32_t tlli, enum gprs_rlcmac_tbf_direction return NULL; } -gprs_rlcmac_tbf *BTS::dl_tbf_by_poll_fn(uint32_t fn, uint8_t trx, uint8_t ts) +gprs_rlcmac_dl_tbf *BTS::dl_tbf_by_poll_fn(uint32_t fn, uint8_t trx, uint8_t ts) { - struct gprs_rlcmac_tbf *tbf; + struct gprs_rlcmac_dl_tbf *tbf; /* only one TBF can poll on specific TS/FN, because scheduler can only * schedule one downlink control block (with polling) at a FN per TS */ @@ -262,14 +262,14 @@ gprs_rlcmac_tbf *BTS::dl_tbf_by_poll_fn(uint32_t fn, uint8_t trx, uint8_t ts) && tbf->poll_fn == fn && tbf->trx->trx_no == trx && tbf->control_ts == ts) { OSMO_ASSERT(tbf->direction == GPRS_RLCMAC_DL_TBF); - return tbf; + return (gprs_rlcmac_dl_tbf *)tbf; } } return NULL; } -gprs_rlcmac_tbf *BTS::ul_tbf_by_poll_fn(uint32_t fn, uint8_t trx, uint8_t ts) +gprs_rlcmac_ul_tbf *BTS::ul_tbf_by_poll_fn(uint32_t fn, uint8_t trx, uint8_t ts) { - struct gprs_rlcmac_tbf *tbf; + struct gprs_rlcmac_ul_tbf *tbf; /* only one TBF can poll on specific TS/FN, because scheduler can only * schedule one downlink control block (with polling) at a FN per TS */ @@ -279,22 +279,22 @@ gprs_rlcmac_tbf *BTS::ul_tbf_by_poll_fn(uint32_t fn, uint8_t trx, uint8_t ts) && tbf->poll_fn == fn && tbf->trx->trx_no == trx && tbf->control_ts == ts) { OSMO_ASSERT(tbf->direction == GPRS_RLCMAC_UL_TBF); - return tbf; + return (gprs_rlcmac_ul_tbf *)tbf; } } return NULL; } /* lookup downlink TBF Entity (by TFI) */ -gprs_rlcmac_tbf *BTS::dl_tbf_by_tfi(uint8_t tfi, uint8_t trx) +gprs_rlcmac_dl_tbf *BTS::dl_tbf_by_tfi(uint8_t tfi, uint8_t trx) { - return tbf_by_tfi(tfi, trx, GPRS_RLCMAC_DL_TBF); + return (gprs_rlcmac_dl_tbf *)tbf_by_tfi(tfi, trx, GPRS_RLCMAC_DL_TBF); } /* lookup uplink TBF Entity (by TFI) */ -gprs_rlcmac_tbf *BTS::ul_tbf_by_tfi(uint8_t tfi, uint8_t trx) +gprs_rlcmac_ul_tbf *BTS::ul_tbf_by_tfi(uint8_t tfi, uint8_t trx) { - return tbf_by_tfi(tfi, trx, GPRS_RLCMAC_UL_TBF); + return (gprs_rlcmac_ul_tbf *)tbf_by_tfi(tfi, trx, GPRS_RLCMAC_UL_TBF); } /* lookup TBF Entity (by TFI) */ @@ -1047,12 +1047,12 @@ gprs_rlcmac_tbf *gprs_rlcmac_pdch::tbf_from_list_by_tfi(struct llist_head *tbf_l return NULL; } -gprs_rlcmac_tbf *gprs_rlcmac_pdch::ul_tbf_by_tfi(uint8_t tfi) +gprs_rlcmac_ul_tbf *gprs_rlcmac_pdch::ul_tbf_by_tfi(uint8_t tfi) { - return tbf_from_list_by_tfi(&bts_data()->ul_tbfs, tfi, GPRS_RLCMAC_UL_TBF); + return (gprs_rlcmac_ul_tbf *)tbf_from_list_by_tfi(&bts_data()->ul_tbfs, tfi, GPRS_RLCMAC_UL_TBF); } -gprs_rlcmac_tbf *gprs_rlcmac_pdch::dl_tbf_by_tfi(uint8_t tfi) +gprs_rlcmac_dl_tbf *gprs_rlcmac_pdch::dl_tbf_by_tfi(uint8_t tfi) { - return tbf_from_list_by_tfi(&bts_data()->dl_tbfs, tfi, GPRS_RLCMAC_DL_TBF); + return (gprs_rlcmac_dl_tbf *)tbf_from_list_by_tfi(&bts_data()->dl_tbfs, tfi, GPRS_RLCMAC_DL_TBF); } diff --git a/src/bts.h b/src/bts.h index a0b808e..8f99942 100644 --- a/src/bts.h +++ b/src/bts.h @@ -62,8 +62,8 @@ struct gprs_rlcmac_pdch { BTS *bts() const; uint8_t trx_no() const; - struct gprs_rlcmac_tbf *ul_tbf_by_tfi(uint8_t tfi); - struct gprs_rlcmac_tbf *dl_tbf_by_tfi(uint8_t tfi); + struct gprs_rlcmac_ul_tbf *ul_tbf_by_tfi(uint8_t tfi); + struct gprs_rlcmac_dl_tbf *dl_tbf_by_tfi(uint8_t tfi); #endif uint8_t m_is_enabled; /* TS is enabled */ @@ -193,12 +193,12 @@ public: /** add paging to paging queue(s) */ int add_paging(uint8_t chan_needed, uint8_t *identity_lv); - gprs_rlcmac_tbf *dl_tbf_by_tlli(uint32_t tlli); - gprs_rlcmac_tbf *ul_tbf_by_tlli(uint32_t tlli); - gprs_rlcmac_tbf *dl_tbf_by_poll_fn(uint32_t fn, uint8_t trx, uint8_t ts); - gprs_rlcmac_tbf *ul_tbf_by_poll_fn(uint32_t fn, uint8_t trx, uint8_t ts); - gprs_rlcmac_tbf *dl_tbf_by_tfi(uint8_t tfi, uint8_t trx); - gprs_rlcmac_tbf *ul_tbf_by_tfi(uint8_t tfi, uint8_t trx); + gprs_rlcmac_dl_tbf *dl_tbf_by_tlli(uint32_t tlli); + gprs_rlcmac_ul_tbf *ul_tbf_by_tlli(uint32_t tlli); + gprs_rlcmac_dl_tbf *dl_tbf_by_poll_fn(uint32_t fn, uint8_t trx, uint8_t ts); + gprs_rlcmac_ul_tbf *ul_tbf_by_poll_fn(uint32_t fn, uint8_t trx, uint8_t ts); + gprs_rlcmac_dl_tbf *dl_tbf_by_tfi(uint8_t tfi, uint8_t trx); + gprs_rlcmac_ul_tbf *ul_tbf_by_tfi(uint8_t tfi, uint8_t trx); int tfi_find_free(enum gprs_rlcmac_tbf_direction dir, uint8_t *_trx, int8_t use_trx); -- 1.8.4.2 From dwillmann at sysmocom.de Wed Jul 16 17:04:31 2014 From: dwillmann at sysmocom.de (Daniel Willmann) Date: Wed, 16 Jul 2014 19:04:31 +0200 Subject: [osmo-pcu 4/5] bts, tbf: Change the TBF return type of functions to the ul/dl version In-Reply-To: <2207c5e4ef0565ab782196a80cc45dcc458938e4.1405530272.git.daniel@totalueberwachung.de> References: <2207c5e4ef0565ab782196a80cc45dcc458938e4.1405530272.git.daniel@totalueberwachung.de> Message-ID: Many functions only ever deal with or return a UL or a DL TBF. Explicitly change the type to reflect which TBF is used where. Ticket: SYS#389 Sponsored-by: On-Waves ehf --- src/bts.cpp | 38 +++++++++++++++++++------------------- src/tbf.cpp | 6 +++--- src/tbf.h | 2 +- 3 files changed, 23 insertions(+), 23 deletions(-) diff --git a/src/bts.cpp b/src/bts.cpp index 68d72f2..8489431 100644 --- a/src/bts.cpp +++ b/src/bts.cpp @@ -417,7 +417,7 @@ int BTS::rcv_imm_ass_cnf(const uint8_t *data, uint32_t fn) int BTS::rcv_rach(uint8_t ra, uint32_t Fn, int16_t qta) { - struct gprs_rlcmac_tbf *tbf; + struct gprs_rlcmac_ul_tbf *tbf; uint8_t trx_no, ts_no = 0; int8_t tfi; /* must be signed */ uint8_t sb = 0; @@ -461,7 +461,7 @@ int BTS::rcv_rach(uint8_t ra, uint32_t Fn, int16_t qta) return -EBUSY; } /* set class to 0, since we don't know the multislot class yet */ - tbf = tbf_alloc(&m_bts, NULL, GPRS_RLCMAC_UL_TBF, tfi, trx_no, 0, 1); + tbf = (gprs_rlcmac_ul_tbf *)tbf_alloc(&m_bts, NULL, GPRS_RLCMAC_UL_TBF, tfi, trx_no, 0, 1); if (!tbf) { LOGP(DRLCMAC, LOGL_NOTICE, "No PDCH resource\n"); /* FIXME: send reject */ @@ -692,7 +692,7 @@ void gprs_rlcmac_pdch::add_paging(struct gprs_rlcmac_paging *pag) */ int gprs_rlcmac_pdch::rcv_data_block_acknowledged(uint8_t *data, uint8_t len, int8_t rssi) { - struct gprs_rlcmac_tbf *tbf; + struct gprs_rlcmac_ul_tbf *tbf; struct rlc_ul_header *rh = (struct rlc_ul_header *)data; switch (len) { @@ -867,24 +867,24 @@ void gprs_rlcmac_pdch::rcv_control_dl_ack_nack(Packet_Downlink_Ack_Nack_t *ack_n void gprs_rlcmac_pdch::rcv_resource_request(Packet_Resource_Request_t *request, uint32_t fn) { - struct gprs_rlcmac_tbf *tbf; + struct gprs_rlcmac_ul_tbf *ul_tbf; + struct gprs_rlcmac_dl_tbf *dl_tbf; struct gprs_rlcmac_sba *sba; int rc; if (request->ID.UnionType) { uint32_t tlli = request->ID.u.TLLI; uint8_t ms_class = 0; - struct gprs_rlcmac_tbf *dl_tbf; uint8_t ta; - tbf = bts()->ul_tbf_by_tlli(tlli); - if (tbf) { + ul_tbf = bts()->ul_tbf_by_tlli(tlli); + if (ul_tbf) { LOGP(DRLCMACUL, LOGL_NOTICE, "Got RACH from " "TLLI=0x%08x while %s still " "exists. Killing pending DL TBF\n", - tlli, tbf_name(tbf)); - tbf_free(tbf); - tbf = NULL; + tlli, tbf_name(ul_tbf)); + tbf_free(ul_tbf); + ul_tbf = NULL; } if ((dl_tbf = bts()->dl_tbf_by_tlli(tlli))) { @@ -918,34 +918,34 @@ void gprs_rlcmac_pdch::rcv_resource_request(Packet_Resource_Request_t *request, ms_class = Decoding::get_ms_class_by_capability(&request->MS_Radio_Access_capability); if (!ms_class) LOGP(DRLCMAC, LOGL_NOTICE, "MS does not give us a class.\n"); - tbf = tbf_alloc_ul(bts_data(), trx_no(), ms_class, tlli, ta, NULL); - if (!tbf) + ul_tbf = tbf_alloc_ul(bts_data(), trx_no(), ms_class, tlli, ta, NULL); + if (!ul_tbf) return; /* set control ts to current MS's TS, until assignment complete */ LOGP(DRLCMAC, LOGL_DEBUG, "Change control TS to %d until assinment is complete.\n", ts_no); - tbf->control_ts = ts_no; + ul_tbf->control_ts = ts_no; /* schedule uplink assignment */ - tbf->ul_ass_state = GPRS_RLCMAC_UL_ASS_SEND_ASS; + ul_tbf->ul_ass_state = GPRS_RLCMAC_UL_ASS_SEND_ASS; return; } if (request->ID.u.Global_TFI.UnionType) { int8_t tfi = request->ID.u.Global_TFI.u.DOWNLINK_TFI; - tbf = bts()->dl_tbf_by_tfi(tfi, trx_no()); - if (!tbf) { + dl_tbf = bts()->dl_tbf_by_tfi(tfi, trx_no()); + if (!dl_tbf) { LOGP(DRLCMAC, LOGL_NOTICE, "PACKET RESSOURCE REQ unknown downlink TFI=%d\n", tfi); return; } } else { int8_t tfi = request->ID.u.Global_TFI.u.UPLINK_TFI; - tbf = bts()->ul_tbf_by_tfi(tfi, trx_no()); - if (!tbf) { + ul_tbf = bts()->ul_tbf_by_tfi(tfi, trx_no()); + if (!ul_tbf) { LOGP(DRLCMAC, LOGL_NOTICE, "PACKET RESSOURCE REQ unknown uplink TFI=%d\n", tfi); return; } } - LOGP(DRLCMAC, LOGL_ERROR, "RX: [PCU <- BTS] %s FIXME: Packet resource request\n", tbf_name(tbf)); + LOGP(DRLCMAC, LOGL_ERROR, "RX: [PCU <- BTS] %s FIXME: Packet resource request\n", tbf_name(ul_tbf)); } void gprs_rlcmac_pdch::rcv_measurement_report(Packet_Measurement_Report_t *report, uint32_t fn) diff --git a/src/tbf.cpp b/src/tbf.cpp index 39549f1..15301a1 100644 --- a/src/tbf.cpp +++ b/src/tbf.cpp @@ -214,12 +214,12 @@ int gprs_rlcmac_tbf::handle(struct gprs_rlcmac_bts *bts, return tbf_new_dl_assignment(bts, imsi, tlli, ms_class, data, len); } -struct gprs_rlcmac_tbf *tbf_alloc_ul(struct gprs_rlcmac_bts *bts, +gprs_rlcmac_ul_tbf *tbf_alloc_ul(struct gprs_rlcmac_bts *bts, int8_t use_trx, uint8_t ms_class, uint32_t tlli, uint8_t ta, struct gprs_rlcmac_tbf *dl_tbf) { uint8_t trx; - struct gprs_rlcmac_tbf *tbf; + struct gprs_rlcmac_ul_tbf *tbf; int8_t tfi; /* must be signed */ #warning "Copy and paste with tbf_new_dl_assignment" @@ -231,7 +231,7 @@ struct gprs_rlcmac_tbf *tbf_alloc_ul(struct gprs_rlcmac_bts *bts, return NULL; } /* use multislot class of downlink TBF */ - tbf = tbf_alloc(bts, dl_tbf, GPRS_RLCMAC_UL_TBF, tfi, trx, ms_class, 0); + tbf = (gprs_rlcmac_ul_tbf *)tbf_alloc(bts, dl_tbf, GPRS_RLCMAC_UL_TBF, tfi, trx, ms_class, 0); if (!tbf) { LOGP(DRLCMAC, LOGL_NOTICE, "No PDCH resource\n"); /* FIXME: send reject */ diff --git a/src/tbf.h b/src/tbf.h index 8464e19..d650021 100644 --- a/src/tbf.h +++ b/src/tbf.h @@ -259,7 +259,7 @@ protected: }; -struct gprs_rlcmac_tbf *tbf_alloc_ul(struct gprs_rlcmac_bts *bts, +struct gprs_rlcmac_ul_tbf *tbf_alloc_ul(struct gprs_rlcmac_bts *bts, int8_t use_trx, uint8_t ms_class, uint32_t tlli, uint8_t ta, struct gprs_rlcmac_tbf *dl_tbf); -- 1.8.4.2 From holger at freyther.de Thu Jul 17 06:52:32 2014 From: holger at freyther.de (Holger Hans Peter Freyther) Date: Thu, 17 Jul 2014 08:52:32 +0200 Subject: [osmo-pcu 4/5] bts, tbf: Change the TBF return type of functions to the ul/dl version In-Reply-To: References: <2207c5e4ef0565ab782196a80cc45dcc458938e4.1405530272.git.daniel@totalueberwachung.de> Message-ID: <20140717065232.GA17208@xiaoyu.lan> On Wed, Jul 16, 2014 at 07:04:31PM +0200, Daniel Willmann wrote: > void gprs_rlcmac_pdch::rcv_resource_request(Packet_Resource_Request_t *request, uint32_t fn) > { > - struct gprs_rlcmac_tbf *tbf; > + struct gprs_rlcmac_ul_tbf *ul_tbf; > + struct gprs_rlcmac_dl_tbf *dl_tbf; Limit the dl_tbf (and ul_tbf) in scope. The dl_tbf one part of the code is dealing with is not the one the other is using. We should not accidently leak a tbf into another scope just because this method is huge. In general cppcheck's style warnings complain about this kind of thing From holger at freyther.de Thu Jul 17 06:55:15 2014 From: holger at freyther.de (Holger Hans Peter Freyther) Date: Thu, 17 Jul 2014 08:55:15 +0200 Subject: [osmo-pcu 4/5] bts, tbf: Change the TBF return type of functions to the ul/dl version In-Reply-To: References: <2207c5e4ef0565ab782196a80cc45dcc458938e4.1405530272.git.daniel@totalueberwachung.de> Message-ID: <20140717065515.GB17208@xiaoyu.lan> On Wed, Jul 16, 2014 at 07:04:31PM +0200, Daniel Willmann wrote: > - LOGP(DRLCMAC, LOGL_ERROR, "RX: [PCU <- BTS] %s FIXME: Packet resource request\n", tbf_name(tbf)); > + LOGP(DRLCMAC, LOGL_ERROR, "RX: [PCU <- BTS] %s FIXME: Packet resource request\n", tbf_name(ul_tbf)); And the compiler just re-inforced me with a warning: home/ich/install/openbsc/include/osmocom/core/logging.h: In member function 'void gprs_rlcmac_pdch::rcv_resource_request(Packet_Resource_Request_t*, uint32_t)': /home/ich/install/openbsc/include/osmocom/core/logging.h:42:53: warning: 'ul_tbf' may be used uninitialized in this function [-Wmaybe-uninitialized] logp2(ss, level, __FILE__, __LINE__, 0, fmt, ##args) After the last if/else either dl_tbf or ul_tbf will be assigned. Maybe just move the warning into the if/else and remove the declaration of the dl_tbf ul_tbf. From dwillmann at sysmocom.de Wed Jul 16 17:04:32 2014 From: dwillmann at sysmocom.de (Daniel Willmann) Date: Wed, 16 Jul 2014 19:04:32 +0200 Subject: [osmo-pcu 5/5] bts, tbf: Split alloc_tbf function into separate UL and DL versions In-Reply-To: <2207c5e4ef0565ab782196a80cc45dcc458938e4.1405530272.git.daniel@totalueberwachung.de> References: <2207c5e4ef0565ab782196a80cc45dcc458938e4.1405530272.git.daniel@totalueberwachung.de> Message-ID: UL and DL tbfs are used in very separate parts and are not the same thing so split the alloc function and use the UL/DL version throughout the code. Ticket: SYS#389 Sponsored-by: On-Waves ehf --- src/bts.cpp | 2 +- src/tbf.cpp | 102 +++++++++++++++++++++++++++++++++------------- src/tbf.h | 9 +++- tests/alloc/AllocTest.cpp | 31 +++++++++----- tests/tbf/TbfTest.cpp | 8 ++-- 5 files changed, 106 insertions(+), 46 deletions(-) diff --git a/src/bts.cpp b/src/bts.cpp index 8489431..5bf139d 100644 --- a/src/bts.cpp +++ b/src/bts.cpp @@ -461,7 +461,7 @@ int BTS::rcv_rach(uint8_t ra, uint32_t Fn, int16_t qta) return -EBUSY; } /* set class to 0, since we don't know the multislot class yet */ - tbf = (gprs_rlcmac_ul_tbf *)tbf_alloc(&m_bts, NULL, GPRS_RLCMAC_UL_TBF, tfi, trx_no, 0, 1); + tbf = tbf_alloc_ul_tbf(&m_bts, NULL, tfi, trx_no, 0, 1); if (!tbf) { LOGP(DRLCMAC, LOGL_NOTICE, "No PDCH resource\n"); /* FIXME: send reject */ diff --git a/src/tbf.cpp b/src/tbf.cpp index 15301a1..1201642 100644 --- a/src/tbf.cpp +++ b/src/tbf.cpp @@ -165,7 +165,7 @@ static int tbf_new_dl_assignment(struct gprs_rlcmac_bts *bts, return -EBUSY; } /* set number of downlink slots according to multislot class */ - tbf = tbf_alloc(bts, tbf, GPRS_RLCMAC_DL_TBF, tfi, trx, ms_class, ss); + tbf = tbf_alloc_dl_tbf(bts, tbf, tfi, trx, ms_class, ss); if (!tbf) { LOGP(DRLCMAC, LOGL_NOTICE, "No PDCH resource\n"); /* FIXME: send reject */ @@ -231,7 +231,7 @@ gprs_rlcmac_ul_tbf *tbf_alloc_ul(struct gprs_rlcmac_bts *bts, return NULL; } /* use multislot class of downlink TBF */ - tbf = (gprs_rlcmac_ul_tbf *)tbf_alloc(bts, dl_tbf, GPRS_RLCMAC_UL_TBF, tfi, trx, ms_class, 0); + tbf = tbf_alloc_ul_tbf(bts, dl_tbf, tfi, trx, ms_class, 0); if (!tbf) { LOGP(DRLCMAC, LOGL_NOTICE, "No PDCH resource\n"); /* FIXME: send reject */ @@ -479,33 +479,20 @@ void gprs_rlcmac_tbf::poll_timeout() LOGP(DRLCMAC, LOGL_ERROR, "- Poll Timeout, but no event!\n"); } -struct gprs_rlcmac_tbf *tbf_alloc(struct gprs_rlcmac_bts *bts, - struct gprs_rlcmac_tbf *old_tbf, enum gprs_rlcmac_tbf_direction dir, - uint8_t tfi, uint8_t trx, +static int setup_tbf(struct gprs_rlcmac_tbf *tbf, struct gprs_rlcmac_bts *bts, + struct gprs_rlcmac_tbf *old_tbf, uint8_t tfi, uint8_t trx, uint8_t ms_class, uint8_t single_slot) { - struct gprs_rlcmac_tbf *tbf; int rc; - LOGP(DRLCMAC, LOGL_DEBUG, "********** TBF starts here **********\n"); - LOGP(DRLCMAC, LOGL_INFO, "Allocating %s TBF: TFI=%d TRX=%d " - "MS_CLASS=%d\n", (dir == GPRS_RLCMAC_UL_TBF) ? "UL" : "DL", - tfi, trx, ms_class); - if (trx >= 8 || tfi >= 32) - return NULL; - - if (dir == GPRS_RLCMAC_UL_TBF) - tbf = talloc_zero(tall_pcu_ctx, struct gprs_rlcmac_ul_tbf); - else - tbf = talloc_zero(tall_pcu_ctx, struct gprs_rlcmac_dl_tbf); + return -1; if (!tbf) - return NULL; + return -1; tbf->m_created_ts = time(NULL); tbf->bts = bts->bts; - tbf->direction = dir; tbf->m_tfi = tfi; tbf->trx = &bts->trx[trx]; tbf->ms_class = ms_class; @@ -514,16 +501,14 @@ struct gprs_rlcmac_tbf *tbf_alloc(struct gprs_rlcmac_bts *bts, single_slot); /* if no resource */ if (rc < 0) { - talloc_free(tbf); - return NULL; + return -1; } /* assign control ts */ tbf->control_ts = 0xff; rc = tbf_assign_control_ts(tbf); /* if no resource */ if (rc < 0) { - talloc_free(tbf); - return NULL; + return -1; } /* set timestamp */ @@ -532,14 +517,73 @@ struct gprs_rlcmac_tbf *tbf_alloc(struct gprs_rlcmac_bts *bts, gettimeofday(&tbf->meas.dl_loss_tv, NULL); tbf->m_llc.init(); - if (dir == GPRS_RLCMAC_UL_TBF) { - llist_add(&tbf->list, &bts->ul_tbfs); - tbf->bts->tbf_ul_created(); - } else { - llist_add(&tbf->list, &bts->dl_tbfs); - tbf->bts->tbf_dl_created(); + return 0; +} + + +struct gprs_rlcmac_ul_tbf *tbf_alloc_ul_tbf(struct gprs_rlcmac_bts *bts, + struct gprs_rlcmac_tbf *old_tbf, uint8_t tfi, uint8_t trx, + uint8_t ms_class, uint8_t single_slot) +{ + struct gprs_rlcmac_ul_tbf *tbf; + int rc; + + LOGP(DRLCMAC, LOGL_DEBUG, "********** TBF starts here **********\n"); + LOGP(DRLCMAC, LOGL_INFO, "Allocating %s TBF: TFI=%d TRX=%d " + "MS_CLASS=%d\n", "UL", tfi, trx, ms_class); + + if (trx >= 8 || tfi >= 32) + return NULL; + + tbf = talloc_zero(tall_pcu_ctx, struct gprs_rlcmac_ul_tbf); + + if (!tbf) + return NULL; + + tbf->direction = GPRS_RLCMAC_UL_TBF; + rc = setup_tbf(tbf, bts, old_tbf, tfi, trx, ms_class, single_slot); + /* if no resource */ + if (rc < 0) { + talloc_free(tbf); + return NULL; + } + + llist_add(&tbf->list, &bts->ul_tbfs); + tbf->bts->tbf_ul_created(); + + return tbf; +} + +struct gprs_rlcmac_dl_tbf *tbf_alloc_dl_tbf(struct gprs_rlcmac_bts *bts, + struct gprs_rlcmac_tbf *old_tbf, uint8_t tfi, uint8_t trx, + uint8_t ms_class, uint8_t single_slot) +{ + struct gprs_rlcmac_dl_tbf *tbf; + int rc; + + LOGP(DRLCMAC, LOGL_DEBUG, "********** TBF starts here **********\n"); + LOGP(DRLCMAC, LOGL_INFO, "Allocating %s TBF: TFI=%d TRX=%d " + "MS_CLASS=%d\n", "DL", tfi, trx, ms_class); + + if (trx >= 8 || tfi >= 32) + return NULL; + + tbf = talloc_zero(tall_pcu_ctx, struct gprs_rlcmac_dl_tbf); + + if (!tbf) + return NULL; + + tbf->direction = GPRS_RLCMAC_DL_TBF; + rc = setup_tbf(tbf, bts, old_tbf, tfi, trx, ms_class, single_slot); + /* if no resource */ + if (rc < 0) { + talloc_free(tbf); + return NULL; } + llist_add(&tbf->list, &bts->dl_tbfs); + tbf->bts->tbf_dl_created(); + return tbf; } diff --git a/src/tbf.h b/src/tbf.h index d650021..4d20987 100644 --- a/src/tbf.h +++ b/src/tbf.h @@ -263,9 +263,14 @@ struct gprs_rlcmac_ul_tbf *tbf_alloc_ul(struct gprs_rlcmac_bts *bts, int8_t use_trx, uint8_t ms_class, uint32_t tlli, uint8_t ta, struct gprs_rlcmac_tbf *dl_tbf); -struct gprs_rlcmac_tbf *tbf_alloc(struct gprs_rlcmac_bts *bts, +struct gprs_rlcmac_ul_tbf *tbf_alloc_ul_tbf(struct gprs_rlcmac_bts *bts, struct gprs_rlcmac_tbf *old_tbf, - enum gprs_rlcmac_tbf_direction dir, uint8_t tfi, uint8_t trx, + uint8_t tfi, uint8_t trx, + uint8_t ms_class, uint8_t single_slot); + +struct gprs_rlcmac_dl_tbf *tbf_alloc_dl_tbf(struct gprs_rlcmac_bts *bts, + struct gprs_rlcmac_tbf *old_tbf, + uint8_t tfi, uint8_t trx, uint8_t ms_class, uint8_t single_slot); void tbf_free(struct gprs_rlcmac_tbf *tbf); diff --git a/tests/alloc/AllocTest.cpp b/tests/alloc/AllocTest.cpp index 80e8c34..830ca90 100644 --- a/tests/alloc/AllocTest.cpp +++ b/tests/alloc/AllocTest.cpp @@ -36,6 +36,17 @@ extern "C" { void *tall_pcu_ctx; int16_t spoof_mnc = 0, spoof_mcc = 0; +static gprs_rlcmac_tbf *tbf_alloc(struct gprs_rlcmac_bts *bts, + struct gprs_rlcmac_tbf *old_tbf, gprs_rlcmac_tbf_direction dir, + uint8_t tfi, uint8_t trx, + uint8_t ms_class, uint8_t single_slot) +{ + if (dir == GPRS_RLCMAC_UL_TBF) + return tbf_alloc_ul_tbf(bts, old_tbf, tfi, trx, ms_class, single_slot); + else + return tbf_alloc_dl_tbf(bts, old_tbf, tfi, trx, ms_class, single_slot); +} + static void test_alloc_a(gprs_rlcmac_tbf_direction dir, const int count) { int tfi; @@ -136,14 +147,14 @@ static void test_alloc_b(int ms_class) tfi = the_bts.tfi_find_free(GPRS_RLCMAC_UL_TBF, &trx_no, -1); OSMO_ASSERT(tfi >= 0); - ul_tbf = tbf_alloc(bts, NULL, GPRS_RLCMAC_UL_TBF, tfi, trx_no, ms_class, 1); + ul_tbf = tbf_alloc_ul_tbf(bts, NULL, tfi, trx_no, ms_class, 1); OSMO_ASSERT(ul_tbf); dump_assignment(ul_tbf, "UL"); /* assume final ack has not been sent */ tfi = the_bts.tfi_find_free(GPRS_RLCMAC_UL_TBF, &trx_no, -1); OSMO_ASSERT(tfi >= 0); - dl_tbf = tbf_alloc(bts, ul_tbf, GPRS_RLCMAC_DL_TBF, tfi, trx_no, ms_class, 0); + dl_tbf = tbf_alloc_dl_tbf(bts, ul_tbf, tfi, trx_no, ms_class, 0); OSMO_ASSERT(dl_tbf); dump_assignment(dl_tbf, "DL"); @@ -177,7 +188,7 @@ static void test_alloc_b(int ms_class) tfi = the_bts.tfi_find_free(GPRS_RLCMAC_UL_TBF, &trx_no, -1); OSMO_ASSERT(tfi >= 0); - dl_tbf = tbf_alloc(bts, NULL, GPRS_RLCMAC_DL_TBF, tfi, trx_no, ms_class, 1); + dl_tbf = tbf_alloc_dl_tbf(bts, NULL, tfi, trx_no, ms_class, 1); dl_tbf->m_tlli = 0x23; dl_tbf->m_tlli_valid = true; OSMO_ASSERT(dl_tbf); @@ -185,7 +196,7 @@ static void test_alloc_b(int ms_class) tfi = the_bts.tfi_find_free(GPRS_RLCMAC_UL_TBF, &trx_no, -1); OSMO_ASSERT(tfi >= 0); - ul_tbf = tbf_alloc(bts, dl_tbf, GPRS_RLCMAC_UL_TBF, tfi, trx_no, ms_class, 0); + ul_tbf = tbf_alloc_ul_tbf(bts, dl_tbf, tfi, trx_no, ms_class, 0); ul_tbf->m_tlli = 0x23; ul_tbf->m_tlli_valid = true; ul_tbf->dir.ul.contention_resolution_done = 1; @@ -226,14 +237,14 @@ static void test_alloc_b(int ms_class) tfi = the_bts.tfi_find_free(GPRS_RLCMAC_UL_TBF, &trx_no, -1); OSMO_ASSERT(tfi >= 0); - ul_tbf = tbf_alloc(bts, NULL, GPRS_RLCMAC_UL_TBF, tfi, trx_no, ms_class, 0); + ul_tbf = tbf_alloc_ul_tbf(bts, NULL, tfi, trx_no, ms_class, 0); OSMO_ASSERT(ul_tbf); dump_assignment(ul_tbf, "UL"); /* assume final ack has not been sent */ tfi = the_bts.tfi_find_free(GPRS_RLCMAC_UL_TBF, &trx_no, -1); OSMO_ASSERT(tfi >= 0); - dl_tbf = tbf_alloc(bts, ul_tbf, GPRS_RLCMAC_DL_TBF, tfi, trx_no, ms_class, 0); + dl_tbf = tbf_alloc_dl_tbf(bts, ul_tbf, tfi, trx_no, ms_class, 0); OSMO_ASSERT(dl_tbf); dump_assignment(dl_tbf, "DL"); @@ -290,13 +301,13 @@ static void test_alloc_b(bool ts0, bool ts1, bool ts2, bool ts3, bool ts4, bool tfi = the_bts.tfi_find_free(GPRS_RLCMAC_UL_TBF, &trx_no, -1); OSMO_ASSERT(tfi >= 0); - ul_tbf = tbf_alloc(bts, NULL, GPRS_RLCMAC_UL_TBF, tfi, trx_no, ms_class, 1); + ul_tbf = tbf_alloc_ul_tbf(bts, NULL, tfi, trx_no, ms_class, 1); OSMO_ASSERT(ul_tbf); /* assume final ack has not been sent */ tfi = the_bts.tfi_find_free(GPRS_RLCMAC_UL_TBF, &trx_no, -1); OSMO_ASSERT(tfi >= 0); - dl_tbf = tbf_alloc(bts, ul_tbf, GPRS_RLCMAC_DL_TBF, tfi, trx_no, ms_class, 0); + dl_tbf = tbf_alloc_dl_tbf(bts, ul_tbf, tfi, trx_no, ms_class, 0); OSMO_ASSERT(dl_tbf); /* verify that both are on the same ts */ @@ -333,14 +344,14 @@ static void test_alloc_b(bool ts0, bool ts1, bool ts2, bool ts3, bool ts4, bool tfi = the_bts.tfi_find_free(GPRS_RLCMAC_UL_TBF, &trx_no, -1); OSMO_ASSERT(tfi >= 0); - dl_tbf = tbf_alloc(bts, NULL, GPRS_RLCMAC_DL_TBF, tfi, trx_no, ms_class, 1); + dl_tbf = tbf_alloc_dl_tbf(bts, NULL, tfi, trx_no, ms_class, 1); OSMO_ASSERT(dl_tbf); dl_tbf->m_tlli = 0x23; dl_tbf->m_tlli_valid = true; tfi = the_bts.tfi_find_free(GPRS_RLCMAC_UL_TBF, &trx_no, -1); OSMO_ASSERT(tfi >= 0); - ul_tbf = tbf_alloc(bts, dl_tbf, GPRS_RLCMAC_UL_TBF, tfi, trx_no, ms_class, 0); + ul_tbf = tbf_alloc_ul_tbf(bts, dl_tbf, tfi, trx_no, ms_class, 0); OSMO_ASSERT(ul_tbf); ul_tbf->m_tlli = 0x23; ul_tbf->m_tlli_valid = true; diff --git a/tests/tbf/TbfTest.cpp b/tests/tbf/TbfTest.cpp index 38975f9..decf4d9 100644 --- a/tests/tbf/TbfTest.cpp +++ b/tests/tbf/TbfTest.cpp @@ -44,16 +44,16 @@ static void test_tbf_tlli_update() /* * Make a uplink and downlink allocation */ - gprs_rlcmac_tbf *dl_tbf = tbf_alloc(the_bts.bts_data(), - NULL, GPRS_RLCMAC_DL_TBF, 0, + gprs_rlcmac_tbf *dl_tbf = tbf_alloc_dl_tbf(the_bts.bts_data(), + NULL, 0, 0, 0, 0); dl_tbf->update_tlli(0x2342); dl_tbf->tlli_mark_valid(); dl_tbf->ta = 4; the_bts.timing_advance()->remember(0x2342, dl_tbf->ta); - gprs_rlcmac_tbf *ul_tbf = tbf_alloc(the_bts.bts_data(), - ul_tbf, GPRS_RLCMAC_UL_TBF, 0, + gprs_rlcmac_tbf *ul_tbf = tbf_alloc_ul_tbf(the_bts.bts_data(), + ul_tbf, 0, 0, 0, 0); ul_tbf->update_tlli(0x2342); ul_tbf->tlli_mark_valid(); -- 1.8.4.2 From holger at freyther.de Thu Jul 17 06:46:24 2014 From: holger at freyther.de (Holger Hans Peter Freyther) Date: Thu, 17 Jul 2014 08:46:24 +0200 Subject: [osmo-pcu 1/5] bts: Ensure tbf direction with OSMO_ASSERT() In-Reply-To: <2207c5e4ef0565ab782196a80cc45dcc458938e4.1405530272.git.daniel@totalueberwachung.de> References: <2207c5e4ef0565ab782196a80cc45dcc458938e4.1405530272.git.daniel@totalueberwachung.de> Message-ID: <20140717064624.GA18946@xiaoyu.lan> On Wed, Jul 16, 2014 at 07:04:28PM +0200, Daniel Willmann wrote: Hi! as we have to move forward I will merge it. One comment in regard to the approach taken here. > +gprs_rlcmac_tbf *gprs_rlcmac_pdch::tbf_from_list_by_tfi(struct llist_head *tbf_list, uint8_t tfi, > + enum gprs_rlcmac_tbf_direction dir) > { > gprs_rlcmac_tbf *tbf; > > llist_for_each_entry(tbf, tbf_list, list) { > + OSMO_ASSERT(tbf->direction == dir); > + return tbf_from_list_by_tfi(&bts_data()->ul_tbfs, tfi, GPRS_RLCMAC_UL_TBF); > + return tbf_from_list_by_tfi(&bts_data()->dl_tbfs, tfi, GPRS_RLCMAC_DL_TBF); assert it on _entry_ into the ul_tbfs and dl_tbfs. If we only have one place where the list is manipulated we can easily pay the price on entry. From dwillmann at sysmocom.de Wed Jul 16 20:24:34 2014 From: dwillmann at sysmocom.de (Daniel Willmann) Date: Wed, 16 Jul 2014 22:24:34 +0200 Subject: [osmo-pcu v2 1/1] bts: Return the special type for {ul, dl}_tbf_by_* functions In-Reply-To: <20140716192337.GL24972@xiaoyu.lan> References: <20140716192337.GL24972@xiaoyu.lan> Message-ID: Start returning the special type instead of the base gprs_rlcmac_tbf when retrieving a TBF. Ticket: SYS#389 Sponsored-by: On-Waves ehf --- src/bts.cpp | 36 ++++++++++++++++++------------------ src/bts.h | 16 ++++++++-------- 2 files changed, 26 insertions(+), 26 deletions(-) diff --git a/src/bts.cpp b/src/bts.cpp index f614dab..79cae4c 100644 --- a/src/bts.cpp +++ b/src/bts.cpp @@ -217,15 +217,15 @@ int BTS::add_paging(uint8_t chan_needed, uint8_t *identity_lv) } /* search for active downlink tbf */ -gprs_rlcmac_tbf *BTS::dl_tbf_by_tlli(uint32_t tlli) +gprs_rlcmac_dl_tbf *BTS::dl_tbf_by_tlli(uint32_t tlli) { - return tbf_by_tlli(tlli, GPRS_RLCMAC_DL_TBF); + return static_cast(tbf_by_tlli(tlli, GPRS_RLCMAC_DL_TBF)); } /* search for active uplink tbf */ -gprs_rlcmac_tbf *BTS::ul_tbf_by_tlli(uint32_t tlli) +gprs_rlcmac_ul_tbf *BTS::ul_tbf_by_tlli(uint32_t tlli) { - return tbf_by_tlli(tlli, GPRS_RLCMAC_UL_TBF); + return static_cast(tbf_by_tlli(tlli, GPRS_RLCMAC_UL_TBF)); } /* search for active downlink or uplink tbf */ @@ -250,9 +250,9 @@ gprs_rlcmac_tbf *BTS::tbf_by_tlli(uint32_t tlli, enum gprs_rlcmac_tbf_direction return NULL; } -gprs_rlcmac_tbf *BTS::dl_tbf_by_poll_fn(uint32_t fn, uint8_t trx, uint8_t ts) +gprs_rlcmac_dl_tbf *BTS::dl_tbf_by_poll_fn(uint32_t fn, uint8_t trx, uint8_t ts) { - struct gprs_rlcmac_tbf *tbf; + struct gprs_rlcmac_dl_tbf *tbf; /* only one TBF can poll on specific TS/FN, because scheduler can only * schedule one downlink control block (with polling) at a FN per TS */ @@ -262,14 +262,14 @@ gprs_rlcmac_tbf *BTS::dl_tbf_by_poll_fn(uint32_t fn, uint8_t trx, uint8_t ts) && tbf->poll_fn == fn && tbf->trx->trx_no == trx && tbf->control_ts == ts) { OSMO_ASSERT(tbf->direction == GPRS_RLCMAC_DL_TBF); - return tbf; + return static_cast(tbf); } } return NULL; } -gprs_rlcmac_tbf *BTS::ul_tbf_by_poll_fn(uint32_t fn, uint8_t trx, uint8_t ts) +gprs_rlcmac_ul_tbf *BTS::ul_tbf_by_poll_fn(uint32_t fn, uint8_t trx, uint8_t ts) { - struct gprs_rlcmac_tbf *tbf; + struct gprs_rlcmac_ul_tbf *tbf; /* only one TBF can poll on specific TS/FN, because scheduler can only * schedule one downlink control block (with polling) at a FN per TS */ @@ -279,22 +279,22 @@ gprs_rlcmac_tbf *BTS::ul_tbf_by_poll_fn(uint32_t fn, uint8_t trx, uint8_t ts) && tbf->poll_fn == fn && tbf->trx->trx_no == trx && tbf->control_ts == ts) { OSMO_ASSERT(tbf->direction == GPRS_RLCMAC_UL_TBF); - return tbf; + return static_cast(tbf); } } return NULL; } /* lookup downlink TBF Entity (by TFI) */ -gprs_rlcmac_tbf *BTS::dl_tbf_by_tfi(uint8_t tfi, uint8_t trx) +gprs_rlcmac_dl_tbf *BTS::dl_tbf_by_tfi(uint8_t tfi, uint8_t trx) { - return tbf_by_tfi(tfi, trx, GPRS_RLCMAC_DL_TBF); + return static_cast(tbf_by_tfi(tfi, trx, GPRS_RLCMAC_DL_TBF)); } /* lookup uplink TBF Entity (by TFI) */ -gprs_rlcmac_tbf *BTS::ul_tbf_by_tfi(uint8_t tfi, uint8_t trx) +gprs_rlcmac_ul_tbf *BTS::ul_tbf_by_tfi(uint8_t tfi, uint8_t trx) { - return tbf_by_tfi(tfi, trx, GPRS_RLCMAC_UL_TBF); + return static_cast(tbf_by_tfi(tfi, trx, GPRS_RLCMAC_UL_TBF)); } /* lookup TBF Entity (by TFI) */ @@ -1047,12 +1047,12 @@ gprs_rlcmac_tbf *gprs_rlcmac_pdch::tbf_from_list_by_tfi(struct llist_head *tbf_l return NULL; } -gprs_rlcmac_tbf *gprs_rlcmac_pdch::ul_tbf_by_tfi(uint8_t tfi) +gprs_rlcmac_ul_tbf *gprs_rlcmac_pdch::ul_tbf_by_tfi(uint8_t tfi) { - return tbf_from_list_by_tfi(&bts_data()->ul_tbfs, tfi, GPRS_RLCMAC_UL_TBF); + return static_cast(tbf_from_list_by_tfi(&bts_data()->ul_tbfs, tfi, GPRS_RLCMAC_UL_TBF)); } -gprs_rlcmac_tbf *gprs_rlcmac_pdch::dl_tbf_by_tfi(uint8_t tfi) +gprs_rlcmac_dl_tbf *gprs_rlcmac_pdch::dl_tbf_by_tfi(uint8_t tfi) { - return tbf_from_list_by_tfi(&bts_data()->dl_tbfs, tfi, GPRS_RLCMAC_DL_TBF); + return static_cast(tbf_from_list_by_tfi(&bts_data()->dl_tbfs, tfi, GPRS_RLCMAC_DL_TBF)); } diff --git a/src/bts.h b/src/bts.h index a0b808e..8f99942 100644 --- a/src/bts.h +++ b/src/bts.h @@ -62,8 +62,8 @@ struct gprs_rlcmac_pdch { BTS *bts() const; uint8_t trx_no() const; - struct gprs_rlcmac_tbf *ul_tbf_by_tfi(uint8_t tfi); - struct gprs_rlcmac_tbf *dl_tbf_by_tfi(uint8_t tfi); + struct gprs_rlcmac_ul_tbf *ul_tbf_by_tfi(uint8_t tfi); + struct gprs_rlcmac_dl_tbf *dl_tbf_by_tfi(uint8_t tfi); #endif uint8_t m_is_enabled; /* TS is enabled */ @@ -193,12 +193,12 @@ public: /** add paging to paging queue(s) */ int add_paging(uint8_t chan_needed, uint8_t *identity_lv); - gprs_rlcmac_tbf *dl_tbf_by_tlli(uint32_t tlli); - gprs_rlcmac_tbf *ul_tbf_by_tlli(uint32_t tlli); - gprs_rlcmac_tbf *dl_tbf_by_poll_fn(uint32_t fn, uint8_t trx, uint8_t ts); - gprs_rlcmac_tbf *ul_tbf_by_poll_fn(uint32_t fn, uint8_t trx, uint8_t ts); - gprs_rlcmac_tbf *dl_tbf_by_tfi(uint8_t tfi, uint8_t trx); - gprs_rlcmac_tbf *ul_tbf_by_tfi(uint8_t tfi, uint8_t trx); + gprs_rlcmac_dl_tbf *dl_tbf_by_tlli(uint32_t tlli); + gprs_rlcmac_ul_tbf *ul_tbf_by_tlli(uint32_t tlli); + gprs_rlcmac_dl_tbf *dl_tbf_by_poll_fn(uint32_t fn, uint8_t trx, uint8_t ts); + gprs_rlcmac_ul_tbf *ul_tbf_by_poll_fn(uint32_t fn, uint8_t trx, uint8_t ts); + gprs_rlcmac_dl_tbf *dl_tbf_by_tfi(uint8_t tfi, uint8_t trx); + gprs_rlcmac_ul_tbf *ul_tbf_by_tfi(uint8_t tfi, uint8_t trx); int tfi_find_free(enum gprs_rlcmac_tbf_direction dir, uint8_t *_trx, int8_t use_trx); -- 1.8.4.2 From max.suraev at fairwaves.co Tue Jul 22 15:07:17 2014 From: max.suraev at fairwaves.co (Max Suraev) Date: Tue, 22 Jul 2014 17:07:17 +0200 Subject: [PATCH] Fix some packaging mistakes detected by lintian. Message-ID: <1406041637-14296-1-git-send-email-max.suraev@fairwaves.co> Signed-off-by: Max Suraev --- debian/changelog | 2 +- debian/control | 9 ++++++++- debian/copyright | 5 +---- 3 files changed, 10 insertions(+), 6 deletions(-) diff --git a/debian/changelog b/debian/changelog index 815d30b..bd2c2b6 100644 --- a/debian/changelog +++ b/debian/changelog @@ -62,6 +62,6 @@ openbsc (0.9.13.115.eb113-1) natty; urgency=low openbsc (0.9.4-1) unstable; urgency=low - * Initial release (Closes: #nnnn) + * Initial release -- Harald Welte Tue, 24 Aug 2010 13:34:24 +0200 diff --git a/debian/control b/debian/control index 7576455..fc7c8ba 100644 --- a/debian/control +++ b/debian/control @@ -3,7 +3,7 @@ Section: net Priority: optional Maintainer: Harald Welte Build-Depends: debhelper (>= 7.0.0~), autotools-dev, pkg-config, libgtp-dev, libosmocore-dev, libosmo-sccp-dev, libdbi0-dev, dh-autoreconf, libosmo-abis-dev, libdbd-sqlite3 -Standards-Version: 3.8.4 +Standards-Version: 3.9.5 Homepage: http://openbsc.osmocom.org/ Vcs-Git: git://bs11-abis.gnumonks.org/openbsc.git Vcs-Browser: http://openbsc.osmocom.org/trac/browser @@ -12,36 +12,43 @@ Package: osmocom-bsc Architecture: any Depends: ${shlibs:Depends}, ${misc:Depends}, libosmocore, libosmo-sccp Description: GSM Base Station Controller; BSC-only version of OpenBSC. Needs a real MSC! + Classical BSC which requires MSC to operate. Package: osmocom-nitb Architecture: any Depends: ${shlibs:Depends}, ${misc:Depends}, libosmocore, libdbd-sqlite3, libdbi1 Description: GSM Network-in-a-Box, implements BSC, MSC, SMSC, HLR, VLR + All the GSM network components bundled together. Package: osmocom-ipaccess-utils Architecture: any Depends: ${shlibs:Depends}, ${misc:Depends}, libosmocore Description: Command line utilities for ip.access nanoBTS + Utilities specific for ip.access unit. Package: osmocom-bs11-utils Architecture: any Depends: ${shlibs:Depends}, ${misc:Depends}, libosmocore Description: Command line utilities for Siemens BS-11 BTS + Utilities specific for BS-11 unit. Package: osmocom-sgsn Architecture: any Depends: ${shlibs:Depends}, ${misc:Depends}, libosmocore, libgtp Description: Osmocom Serving GPRS Support Node + SGSN implementation. Package: osmocom-gbproxy Architecture: any Depends: ${shlibs:Depends}, ${misc:Depends}, libosmocore Description: Osmocom GPRS Gb Interface Proxy + Proxy for Gb interface. Package: osmocom-bsc-nat Architecture: any Depends: ${shlibs:Depends}, ${misc:Depends}, libosmocore Description: Osmocom Base Station Controller Network Address Translation + Network address translation for BSC. Package: osmocom-bsc-dbg Architecture: any diff --git a/debian/copyright b/debian/copyright index 09693c9..fbac90c 100644 --- a/debian/copyright +++ b/debian/copyright @@ -6,7 +6,7 @@ It was downloaded from: git://bs11-abis.gnumonks.org/openbsc.git -Upstream Author(s): +Upstream Authors: Harald Welte Dieter Spaar @@ -45,6 +45,3 @@ The Debian packaging is: and is licensed under the GPL version 3, see "/usr/share/common-licenses/GPL-3". - -# Please also look if there are files or directories which have a -# different copyright/license attached and list them here. -- 1.9.1 From Max.Suraev at fairwaves.co Tue Jul 22 15:13:20 2014 From: Max.Suraev at fairwaves.co (=?UTF-8?B?4piO?=) Date: Tue, 22 Jul 2014 17:13:20 +0200 Subject: [PATCH] Fix some packaging mistakes detected by lintian. In-Reply-To: <1406041637-14296-1-git-send-email-max.suraev@fairwaves.co> References: <1406041637-14296-1-git-send-email-max.suraev@fairwaves.co> Message-ID: <53CE7F90.7050202@fairwaves.co> Since the latest discussion about uploading .deb packages into official Debian repo I've decided to help a bit by fixing various errors and warnings. All the errors are fixed except for those related to start/stop scripts because I think the right course would be to drop them entirely and use systemd's .service files instead. The remaining warnings are either about lack of manpage or some debian-specific changelog version magic which I've failed to understand from reading its description - someone with better English skills should volunteer to fix both :) -- best regards, Max, http://fairwaves.co From holger at freyther.de Wed Jul 30 06:46:22 2014 From: holger at freyther.de (Holger Hans Peter Freyther) Date: Wed, 30 Jul 2014 08:46:22 +0200 Subject: [PATCH] Fix some packaging mistakes detected by lintian. In-Reply-To: <1406041637-14296-1-git-send-email-max.suraev@fairwaves.co> References: <1406041637-14296-1-git-send-email-max.suraev@fairwaves.co> Message-ID: <20140730064622.GU5744@xiaoyu.lan> On Tue, Jul 22, 2014 at 05:07:17PM +0200, Max Suraev wrote: > -Standards-Version: 3.8.4 > +Standards-Version: 3.9.5 So on which distributions can we build packages then. Using the latest version is all nice but if I can't build for Debian 6.0 then you didn't do me a favor. :) holger From ravi.varun00 at gmail.com Mon Jul 28 06:39:09 2014 From: ravi.varun00 at gmail.com (Ravi Shankar) Date: Mon, 28 Jul 2014 12:09:09 +0530 Subject: Request for the Network Measurement Report info Message-ID: Dear Sir Is it possible to get the Network Measurement Reports (NMRs) (This report comprises of Serving and neighboring cell-id , received signal strengths, timing advance, time of arrival values etc) of a particular Number/IMSI using OpenBSC. I am aware that we get these fields from the normal BSC. Regards. Ravi -------------- next part -------------- An HTML attachment was scrubbed... URL: