diff options
author | Holger Hans Peter Freyther <holger@moiji-mobile.com> | 2013-07-13 15:23:58 +0200 |
---|---|---|
committer | Ivan Kluchnikov <kluchnikovi@gmail.com> | 2013-07-30 12:23:25 +0400 |
commit | 98fe945a0d54fcce20f99ad3f02f36fdd178d044 (patch) | |
tree | c8b7a5302728f433a044204717a1de47315bdf41 /src | |
parent | 249c7e943129de9192a0102cfbd8d6263166e11b (diff) |
misc: Move the parsing of the ms_class from RA Capabilities to a method
Decrease the number of lines of a single method by splitting things up.
The fewer lines of code, branches and side-effects in a method, the easier
it will be to understand. The other benefit is that one can start creating
unit tests for the some parts of the code.
Diffstat (limited to 'src')
-rw-r--r-- | src/gprs_bssgp_pcu.cpp | 75 |
1 files changed, 43 insertions, 32 deletions
diff --git a/src/gprs_bssgp_pcu.cpp b/src/gprs_bssgp_pcu.cpp index b90f2c57..e994f9fa 100644 --- a/src/gprs_bssgp_pcu.cpp +++ b/src/gprs_bssgp_pcu.cpp @@ -71,6 +71,47 @@ static int parse_imsi(struct tlv_parsed *tp, char *imsi) return 0; } +static int parse_ra_cap_ms_class(struct tlv_parsed *tp) +{ + bitvec *block; + unsigned rp = 0; + uint8_t ms_class = 0; + uint8_t cap_len; + uint8_t *cap; + + if (!TLVP_PRESENT(tp, BSSGP_IE_MS_RADIO_ACCESS_CAP)) + return ms_class; + + cap_len = TLVP_LEN(tp, BSSGP_IE_MS_RADIO_ACCESS_CAP); + cap = (uint8_t *) TLVP_VAL(tp, BSSGP_IE_MS_RADIO_ACCESS_CAP); + + block = bitvec_alloc(cap_len); + bitvec_unpack(block, cap); + bitvec_read_field(block, rp, 4); // Access Technology Type + bitvec_read_field(block, rp, 7); // Length of Access Capabilities + bitvec_read_field(block, rp, 3); // RF Power Capability + if (bitvec_read_field(block, rp, 1)) // A5 Bits Present + bitvec_read_field(block, rp, 7); // A5 Bits + bitvec_read_field(block, rp, 1); // ES IND + bitvec_read_field(block, rp, 1); // PS + bitvec_read_field(block, rp, 1); // VGCS + bitvec_read_field(block, rp, 1); // VBS + if (bitvec_read_field(block, rp, 1)) { // Multislot Cap Present + if (bitvec_read_field(block, rp, 1)) // HSCSD Present + bitvec_read_field(block, rp, 5); // Class + if (bitvec_read_field(block, rp, 1)) { // GPRS Present + ms_class = bitvec_read_field(block, rp, 5); // Class + bitvec_read_field(block, rp, 1); // Ext. + } + if (bitvec_read_field(block, rp, 1)) // SMS Present + bitvec_read_field(block, rp, 4); // SMS Value + bitvec_read_field(block, rp, 4); // SMS Value + } + + bitvec_free(block); + return ms_class; +} + int gprs_bssgp_pcu_rx_dl_ud(struct msgb *msg, struct tlv_parsed *tp) { struct bssgp_ud_hdr *budh; @@ -107,38 +148,8 @@ int gprs_bssgp_pcu_rx_dl_ud(struct msgb *msg, struct tlv_parsed *tp) parse_imsi(tp, imsi); /* parse ms radio access capability */ - uint8_t ms_class = 0; - if (TLVP_PRESENT(tp, BSSGP_IE_MS_RADIO_ACCESS_CAP)) - { - bitvec *block; - uint8_t cap_len = TLVP_LEN(tp, BSSGP_IE_MS_RADIO_ACCESS_CAP); - uint8_t *cap = (uint8_t *) TLVP_VAL(tp, BSSGP_IE_MS_RADIO_ACCESS_CAP); - unsigned rp = 0; - - block = bitvec_alloc(cap_len); - bitvec_unpack(block, cap); - bitvec_read_field(block, rp, 4); // Access Technology Type - bitvec_read_field(block, rp, 7); // Length of Access Capabilities - bitvec_read_field(block, rp, 3); // RF Power Capability - if (bitvec_read_field(block, rp, 1)) // A5 Bits Present - bitvec_read_field(block, rp, 7); // A5 Bits - bitvec_read_field(block, rp, 1); // ES IND - bitvec_read_field(block, rp, 1); // PS - bitvec_read_field(block, rp, 1); // VGCS - bitvec_read_field(block, rp, 1); // VBS - if (bitvec_read_field(block, rp, 1)) { // Multislot Cap Present - if (bitvec_read_field(block, rp, 1)) // HSCSD Present - bitvec_read_field(block, rp, 5); // Class - if (bitvec_read_field(block, rp, 1)) { // GPRS Present - ms_class = bitvec_read_field(block, rp, 5); // Class - bitvec_read_field(block, rp, 1); // Ext. - } - if (bitvec_read_field(block, rp, 1)) // SMS Present - bitvec_read_field(block, rp, 4); // SMS Value - bitvec_read_field(block, rp, 4); // SMS Value - } - bitvec_free(block); - } + uint8_t ms_class = parse_ra_cap_ms_class(tp); + /* get lifetime */ uint16_t delay_csec = 0xffff; if (TLVP_PRESENT(tp, BSSGP_IE_PDU_LIFETIME)) |