diff options
-rw-r--r-- | src/gb/gprs_ns.c | 68 | ||||
-rw-r--r-- | tests/gb/gprs_ns_test.ok | 49 |
2 files changed, 67 insertions, 50 deletions
diff --git a/src/gb/gprs_ns.c b/src/gb/gprs_ns.c index a597c2c0..043a66c0 100644 --- a/src/gb/gprs_ns.c +++ b/src/gb/gprs_ns.c @@ -114,7 +114,7 @@ static const struct rate_ctr_desc nsvc_ctr_description[] = { { "blocked", "NS-VC Block count " }, { "dead", "NS-VC gone dead count " }, { "replaced", "NS-VC replaced other count" }, - { "nsei-chg", "NS-VC changed NSEI " }, + { "nsei-chg", "NS-VC changed NSEI count " }, { "inv-nsvci", "NS-VCI was invalid count " }, { "inv-nsei", "NSEI was invalid count " }, }; @@ -769,10 +769,8 @@ static int gprs_ns_rx_reset(struct gprs_nsvc **nsvc, struct msgb *msg) (*nsvc)->nsvci, (*nsvc)->nsvci_is_valid ? "" : "(invalid)", nsei, nsvci, gprs_ns_cause_str(cause)); - if (!(*nsvc)->nsvci_is_valid) { - /* It's a new uninitialised NS-VC, nothing to check here */ - } else if ((*nsvc)->nsvci != nsvci) { - if ((*nsvc)->remote_end_is_sgsn) { + if ((*nsvc)->nsvci_is_valid && (*nsvc)->nsvci != nsvci) { + if ((*nsvc)->persistent || (*nsvc)->remote_end_is_sgsn) { /* The incoming RESET doesn't match the NSVCI. Send an * appropriate RESET_ACK and ignore the RESET. * See 3GPP TS 08.16, 7.3.1, 2nd paragraph. @@ -787,18 +785,25 @@ static int gprs_ns_rx_reset(struct gprs_nsvc **nsvc, struct msgb *msg) /* NS-VCI has changed */ gprs_nsvc_replace_if_found(nsvci, nsvc, &orig_nsvc); + } - } else if ((*nsvc)->nsei != nsei) { - /* The incoming RESET doesn't match the NSEI. Send an - * appropriate RESET_ACK and ignore the RESET. - * See 3GPP TS 08.16, 7.3.1, 3rd paragraph. - */ - ns_osmo_signal_dispatch_mismatch(*nsvc, msg, - NS_PDUT_RESET, - NS_IE_NSEI); - rate_ctr_inc(&(*nsvc)->ctrg->ctr[NS_CTR_INV_NSEI]); - gprs_ns_tx_reset_ack(*nsvc); - return 0; + if ((*nsvc)->nsvci_is_valid && (*nsvc)->nsei != nsei) { + if ((*nsvc)->persistent || (*nsvc)->remote_end_is_sgsn) { + /* The incoming RESET doesn't match the NSEI. Send an + * appropriate RESET_ACK and ignore the RESET. + * See 3GPP TS 08.16, 7.3.1, 3rd paragraph. + */ + ns_osmo_signal_dispatch_mismatch(*nsvc, msg, + NS_PDUT_RESET, + NS_IE_NSEI); + rate_ctr_inc(&(*nsvc)->ctrg->ctr[NS_CTR_INV_NSEI]); + gprs_ns_tx_reset_ack(*nsvc); + return 0; + } + + /* NSEI has changed */ + rate_ctr_inc(&(*nsvc)->ctrg->ctr[NS_CTR_NSEI_CHG]); + (*nsvc)->nsei = nsei; } /* Mark NS-VC as blocked and alive */ @@ -885,7 +890,8 @@ static int gprs_ns_rx_reset_ack(struct gprs_nsvc **nsvc, struct msgb *msg) int use_other_nsvc; /* Only do this with BSS peers */ - use_other_nsvc = !(*nsvc)->remote_end_is_sgsn; + use_other_nsvc = !(*nsvc)->remote_end_is_sgsn && + !(*nsvc)->persistent; if (use_other_nsvc) /* Update *nsvc to point to the right NSVC object */ @@ -916,17 +922,23 @@ static int gprs_ns_rx_reset_ack(struct gprs_nsvc **nsvc, struct msgb *msg) gprs_ns_ll_copy(*nsvc, orig_nsvc); gprs_ns_ll_clear(orig_nsvc); } else if ((*nsvc)->nsei != nsei) { - /* The incoming RESET_ACK doesn't match the NSEI. - * See 3GPP TS 08.16, 7.3.1, 4th paragraph. - */ - ns_osmo_signal_dispatch_mismatch(*nsvc, msg, - NS_PDUT_RESET_ACK, - NS_IE_NSEI); - rate_ctr_inc(&(*nsvc)->ctrg->ctr[NS_CTR_INV_NSEI]); - LOGP(DNS, LOGL_ERROR, - "NS RESET ACK Unknown NSEI %d (NS-VCI=%u) from %s\n", - nsei, nsvci, gprs_ns_ll_str(*nsvc)); - return -EINVAL; + if ((*nsvc)->persistent || (*nsvc)->remote_end_is_sgsn) { + /* The incoming RESET_ACK doesn't match the NSEI. + * See 3GPP TS 08.16, 7.3.1, 4th paragraph. + */ + ns_osmo_signal_dispatch_mismatch(*nsvc, msg, + NS_PDUT_RESET_ACK, + NS_IE_NSEI); + rate_ctr_inc(&(*nsvc)->ctrg->ctr[NS_CTR_INV_NSEI]); + LOGP(DNS, LOGL_ERROR, + "NS RESET ACK Unknown NSEI %d (NS-VCI=%u) from %s\n", + nsei, nsvci, gprs_ns_ll_str(*nsvc)); + return -EINVAL; + } + + /* NSEI has changed */ + rate_ctr_inc(&(*nsvc)->ctrg->ctr[NS_CTR_NSEI_CHG]); + (*nsvc)->nsei = nsei; } /* Mark NS-VC as blocked and alive */ diff --git a/tests/gb/gprs_ns_test.ok b/tests/gb/gprs_ns_test.ok index a882488a..5f90d03f 100644 --- a/tests/gb/gprs_ns_test.ok +++ b/tests/gb/gprs_ns_test.ok @@ -186,7 +186,7 @@ result (RESET) = 9 Current NS-VCIs: VCI 0x3344, NSEI 0x1122, peer 0x01020304:3333, blocked VCI 0x1122, NSEI 0x3344, peer 0x01020304:4444, blocked - NS-VC changed NSEI : 1 + NS-VC changed NSEI count : 1 --- Peer port 3333, RESET, VCI is changed back --- @@ -196,7 +196,7 @@ PROCESSING RESET from 0x01020304:3333 ==> got signal NS_REPLACED: 0x1122/1.2.3.4:4444 -> 0x3344/1.2.3.4:3333 ==> got signal NS_RESET, NS-VC 0x1122/1.2.3.4:3333 MESSAGE to BSS, msg length 9 -03 01 82 11 22 04 82 33 44 +03 01 82 11 22 04 82 11 22 MESSAGE to BSS, msg length 1 0a @@ -205,9 +205,9 @@ result (RESET) = 9 Current NS-VCIs: VCI 0x3344, NSEI 0x1122, peer 0x00000000:0, blocked - VCI 0x1122, NSEI 0x3344, peer 0x01020304:3333, blocked + VCI 0x1122, NSEI 0x1122, peer 0x01020304:3333, blocked NS-VC replaced other count: 1 - NS-VC changed NSEI : 1 + NS-VC changed NSEI count : 2 --- Peer port 4444, RESET, NSEI is changed back --- @@ -227,7 +227,7 @@ Current NS-VCIs: VCI 0x3344, NSEI 0x1122, peer 0x00000000:0, blocked VCI 0x1122, NSEI 0x1122, peer 0x01020304:4444, blocked NS-VC replaced other count: 1 - NS-VC changed NSEI : 2 + NS-VC changed NSEI count : 2 --- Setup VC 1 BSS -> SGSN --- @@ -424,18 +424,21 @@ Current NS-VCIs: PROCESSING RESET from 0x01020304:2222 02 00 81 01 01 82 10 01 04 82 f0 00 -==> got signal NS_MISMATCH: 0x1001/1.2.3.4:2222 pdu=2, ie=4 +==> got signal NS_RESET, NS-VC 0x1001/1.2.3.4:2222 MESSAGE to BSS, msg length 9 -03 01 82 10 01 04 82 10 00 +03 01 82 10 01 04 82 f0 00 -result (RESET) = 0 +MESSAGE to BSS, msg length 1 +0a + +result (RESET) = 9 Current NS-VCIs: VCI 0x2001, NSEI 0x2000, peer 0x01020304:1111 - VCI 0x1001, NSEI 0x1000, peer 0x01020304:2222, blocked + VCI 0x1001, NSEI 0xf000, peer 0x01020304:2222, blocked NS-VC Block count : 3 NS-VC replaced other count: 1 - NSEI was invalid count : 1 + NS-VC changed NSEI count : 1 --- RESET with invalid NSVCI, BSS -> SGSN --- @@ -456,7 +459,7 @@ Current NS-VCIs: VCI 0xf001, NSEI 0x1000, peer 0x01020304:2222, blocked NS-VC Block count : 3 NS-VC replaced other count: 1 - NSEI was invalid count : 1 + NS-VC changed NSEI count : 2 --- RESET with old NSEI, NSVCI, BSS -> SGSN --- @@ -477,7 +480,7 @@ Current NS-VCIs: VCI 0x1001, NSEI 0x1000, peer 0x01020304:2222, blocked NS-VC Block count : 3 NS-VC replaced other count: 1 - NSEI was invalid count : 1 + NS-VC changed NSEI count : 2 --- Unexpected RESET_ACK VC 1, BSS -> SGSN --- @@ -491,7 +494,7 @@ Current NS-VCIs: VCI 0x1001, NSEI 0x1000, peer 0x01020304:2222, blocked NS-VC Block count : 3 NS-VC replaced other count: 1 - NSEI was invalid count : 1 + NS-VC changed NSEI count : 2 --- RESET_ACK with invalid NSEI, BSS -> SGSN --- @@ -501,20 +504,22 @@ MESSAGE to BSS, msg length 12 PROCESSING RESET_ACK from 0x01020304:2222 03 01 82 10 01 04 82 f0 00 -==> got signal NS_MISMATCH: 0x1001/1.2.3.4:2222 pdu=3, ie=4 -result (RESET_ACK) = -22 +MESSAGE to BSS, msg length 1 +0a + +result (RESET_ACK) = 1 Current NS-VCIs: VCI 0x2001, NSEI 0x2000, peer 0x01020304:1111 - VCI 0x1001, NSEI 0x1000, peer 0x01020304:2222, blocked - NS-VC Block count : 3 + VCI 0x1001, NSEI 0xf000, peer 0x01020304:2222, blocked + NS-VC Block count : 4 NS-VC replaced other count: 1 - NSEI was invalid count : 2 + NS-VC changed NSEI count : 3 --- RESET_ACK with invalid NSVCI, BSS -> SGSN --- MESSAGE to BSS, msg length 12 -02 00 81 01 01 82 10 01 04 82 10 00 +02 00 81 01 01 82 10 01 04 82 f0 00 PROCESSING RESET_ACK from 0x01020304:2222 03 01 82 f0 01 04 82 10 00 @@ -524,11 +529,11 @@ result (RESET_ACK) = -22 Current NS-VCIs: VCI 0x2001, NSEI 0x2000, peer 0x01020304:1111 - VCI 0x1001, NSEI 0x1000, peer 0x01020304:2222, blocked - NS-VC Block count : 3 + VCI 0x1001, NSEI 0xf000, peer 0x01020304:2222, blocked + NS-VC Block count : 4 NS-VC replaced other count: 1 + NS-VC changed NSEI count : 3 NS-VCI was invalid count : 1 - NSEI was invalid count : 2 Current NS-VCIs: |