pespin has submitted this change. (
https://gerrit.osmocom.org/c/libosmo-gprs/+/35783?usp=email )
Change subject: rlcmac: ul_tbf: Register UL ACK/NACK poll inside FSM
......................................................................
rlcmac: ul_tbf: Register UL ACK/NACK poll inside FSM
The poll is part of the FSM mechanism to get events to transit over the
different states. Register it from within the FSM to have more fine
grained control as well as have knowledge about the FN being reserved.
This knowledge will be used ina follow up patch for the UL TBF to wait
for the correct PKT CTRL ACK BLOCk.conf.
Change-Id: Iaa8ad8052b9f3b52b05af2b7fc9cb8172f1b6bb7
---
M include/osmocom/gprs/rlcmac/tbf_ul.h
M include/osmocom/gprs/rlcmac/tbf_ul_fsm.h
M src/rlcmac/rlcmac.c
M src/rlcmac/tbf_ul.c
M src/rlcmac/tbf_ul_fsm.c
M tests/rlcmac/rlcmac_prim_test.err
6 files changed, 67 insertions(+), 27 deletions(-)
Approvals:
fixeria: Looks good to me, but someone else must approve
pespin: Looks good to me, approved
Jenkins Builder: Verified
diff --git a/include/osmocom/gprs/rlcmac/tbf_ul.h b/include/osmocom/gprs/rlcmac/tbf_ul.h
index c30a566..847b965 100644
--- a/include/osmocom/gprs/rlcmac/tbf_ul.h
+++ b/include/osmocom/gprs/rlcmac/tbf_ul.h
@@ -71,7 +71,7 @@
struct msgb *gprs_rlcmac_ul_tbf_dummy_create(struct gprs_rlcmac_ul_tbf *ul_tbf);
int gprs_rlcmac_ul_tbf_handle_pkt_ul_ack_nack(struct gprs_rlcmac_ul_tbf *ul_tbf,
- const RlcMacDownlink_t *dl_block);
+ const struct gprs_rlcmac_dl_block_ind *dlbi);
int gprs_rlcmac_ul_tbf_handle_pkt_ul_ass(struct gprs_rlcmac_ul_tbf *ul_tbf,
const struct gprs_rlcmac_dl_block_ind *dlbi);
diff --git a/include/osmocom/gprs/rlcmac/tbf_ul_fsm.h
b/include/osmocom/gprs/rlcmac/tbf_ul_fsm.h
index 059dad4..e3aeb3f 100644
--- a/include/osmocom/gprs/rlcmac/tbf_ul_fsm.h
+++ b/include/osmocom/gprs/rlcmac/tbf_ul_fsm.h
@@ -42,8 +42,7 @@
};
struct tbf_ul_ass_ev_rx_ul_ack_nack {
- bool final_ack;
- bool tbf_est;
+ const struct gprs_rlcmac_dl_block_ind *dlbi;
};
int gprs_rlcmac_tbf_ul_fsm_init(void);
diff --git a/src/rlcmac/rlcmac.c b/src/rlcmac/rlcmac.c
index e99ebb7..525398b 100644
--- a/src/rlcmac/rlcmac.c
+++ b/src/rlcmac/rlcmac.c
@@ -710,16 +710,7 @@
dlbi->ts_nr, dlbi->fn, pkt_ul_ack->UPLINK_TFI);
return -ENOENT;
}
-
- rc = gprs_rlcmac_ul_tbf_handle_pkt_ul_ack_nack(ul_tbf, &dlbi->dl_block);
-
- /* If RRBP contains valid data, schedule a response (PKT CONTROL ACK or PKT RESOURCE
REQ). */
- if (dlbi->dl_block.SP) {
- uint32_t poll_fn = rrbp2fn(dlbi->fn, dlbi->dl_block.RRBP);
- gprs_rlcmac_pdch_ulc_reserve(g_rlcmac_ctx->sched.ulc[dlbi->ts_nr], poll_fn,
- GPRS_RLCMAC_PDCH_ULC_POLL_UL_ACK,
- ul_tbf_as_tbf(ul_tbf));
- }
+ rc = gprs_rlcmac_ul_tbf_handle_pkt_ul_ack_nack(ul_tbf, dlbi);
return rc;
}
diff --git a/src/rlcmac/tbf_ul.c b/src/rlcmac/tbf_ul.c
index c6d81d4..3d4ba2b 100644
--- a/src/rlcmac/tbf_ul.c
+++ b/src/rlcmac/tbf_ul.c
@@ -305,9 +305,9 @@
}
int gprs_rlcmac_ul_tbf_handle_pkt_ul_ack_nack(struct gprs_rlcmac_ul_tbf *ul_tbf,
- const RlcMacDownlink_t *dl_block)
+ const struct gprs_rlcmac_dl_block_ind *dlbi)
{
- const Packet_Uplink_Ack_Nack_t *ack = &dl_block->u.Packet_Uplink_Ack_Nack;
+ const Packet_Uplink_Ack_Nack_t *ack = &dlbi->dl_block.u.Packet_Uplink_Ack_Nack;
const PU_AckNack_GPRS_t *gprs = &ack->u.PU_AckNack_GPRS_Struct;
const Ack_Nack_Description_t *ack_desc = &gprs->Ack_Nack_Description;
int bsn_begin, bsn_end;
@@ -321,8 +321,7 @@
};
int rc;
struct tbf_ul_ass_ev_rx_ul_ack_nack ev_ack = {
- .final_ack = ack_desc->FINAL_ACK_INDICATION,
- .tbf_est = (gprs->Exist_AdditionsR99 && gprs->AdditionsR99.TBF_EST),
+ .dlbi = dlbi,
};
num_blocks = gprs_rlcmac_decode_gprs_acknack_bits(
diff --git a/src/rlcmac/tbf_ul_fsm.c b/src/rlcmac/tbf_ul_fsm.c
index 0949ca6..92d1d64 100644
--- a/src/rlcmac/tbf_ul_fsm.c
+++ b/src/rlcmac/tbf_ul_fsm.c
@@ -27,8 +27,11 @@
#include <osmocom/gprs/rlcmac/tbf_ul.h>
#include <osmocom/gprs/rlcmac/rlc_window_ul.h>
#include <osmocom/gprs/rlcmac/gre.h>
+#include <osmocom/gprs/rlcmac/pdch_ul_controller.h>
#define X(s) (1 << (s))
+#define LOGPFSMLDLBI(fi, dlbi, lvl, fmt, args...) \
+ LOGPFSML(fi, lvl, "(ts=%u,fn=%u) " fmt, (dlbi)->ts_nr, (dlbi)->fn, ##
args)
static const struct value_string tbf_ul_fsm_event_names[] = {
{ GPRS_RLCMAC_TBF_UL_EV_UL_ASS_START, "UL_ASS_START" },
@@ -198,12 +201,30 @@
reinit_pkt_acces_procedure(ctx);
break;
case GPRS_RLCMAC_TBF_UL_EV_RX_UL_ACK_NACK:
+ {
+ struct tbf_ul_ass_ev_rx_ul_ack_nack *ctx_ul_ack_nack = (struct
tbf_ul_ass_ev_rx_ul_ack_nack *)data;
+ const struct gprs_rlcmac_dl_block_ind *dlbi = ctx_ul_ack_nack->dlbi;
+ const Packet_Uplink_Ack_Nack_t *ack = &dlbi->dl_block.u.Packet_Uplink_Ack_Nack;
+ const PU_AckNack_GPRS_t *gprs = &ack->u.PU_AckNack_GPRS_Struct;
+ const Ack_Nack_Description_t *ack_desc = &gprs->Ack_Nack_Description;
+
if (gprs_rlcmac_ul_tbf_in_contention_resolution(ctx->ul_tbf)) {
_contention_resolution_succeeded(ctx);
}
+ /* If RRBP contains valid data, schedule a response (PKT CONTROL ACK or PKT RESOURCE
REQ). */
+ if (dlbi->dl_block.SP) {
+ uint32_t poll_fn = rrbp2fn(dlbi->fn, dlbi->dl_block.RRBP);
+ gprs_rlcmac_pdch_ulc_reserve(g_rlcmac_ctx->sched.ulc[dlbi->ts_nr], poll_fn,
+ GPRS_RLCMAC_PDCH_ULC_POLL_UL_ACK,
+ ul_tbf_as_tbf(ctx->ul_tbf));
+ }
/* It's impossible we receive a correct final_ack here, since we didn't
* sent last data (FSM would be in FINISHED state then) */
+ if (ack_desc->FINAL_ACK_INDICATION)
+ LOGPFSMLDLBI(ctx->fi, dlbi, LOGL_INFO, "Rx unexpected final_ack while not
finished sending blocks. Network bug!\n");
+
break;
+ }
case GPRS_RLCMAC_TBF_UL_EV_LAST_UL_DATA_SENT:
arm_T3182_if_needed(ctx);
tbf_ul_fsm_state_chg(fi, GPRS_RLCMAC_TBF_UL_ST_FINISHED);
@@ -216,13 +237,18 @@
static void st_finished(struct osmo_fsm_inst *fi, uint32_t event, void *data)
{
struct gprs_rlcmac_tbf_ul_fsm_ctx *ctx = (struct gprs_rlcmac_tbf_ul_fsm_ctx
*)fi->priv;
- struct tbf_ul_ass_ev_rx_ul_ack_nack *ctx_ul_ack_nack;
switch (event) {
case GPRS_RLCMAC_TBF_UL_EV_N3104_MAX:
reinit_pkt_acces_procedure(ctx);
break;
case GPRS_RLCMAC_TBF_UL_EV_RX_UL_ACK_NACK:
- ctx_ul_ack_nack = (struct tbf_ul_ass_ev_rx_ul_ack_nack *)data;
+ {
+ struct tbf_ul_ass_ev_rx_ul_ack_nack *ctx_ul_ack_nack = (struct
tbf_ul_ass_ev_rx_ul_ack_nack *)data;
+ const struct gprs_rlcmac_dl_block_ind *dlbi = ctx_ul_ack_nack->dlbi;
+ const Packet_Uplink_Ack_Nack_t *ack = &dlbi->dl_block.u.Packet_Uplink_Ack_Nack;
+ const PU_AckNack_GPRS_t *gprs = &ack->u.PU_AckNack_GPRS_Struct;
+ const Ack_Nack_Description_t *ack_desc = &gprs->Ack_Nack_Description;
+
if (gprs_rlcmac_ul_tbf_in_contention_resolution(ctx->ul_tbf)) {
_contention_resolution_succeeded(ctx);
} else if (fi->T == 3182 && osmo_timer_pending(&fi->timer)) {
@@ -230,16 +256,25 @@
* the mobile station shall stop timer T3182 for the TBF".
* In our case we only use T3128 once we are out of contention resolution (T3166)
*/
- LOGPFSML(ctx->fi, LOGL_DEBUG, "Rx Pkt UL ACK/NACK, stop T3182\n");
+ LOGPFSMLDLBI(ctx->fi, dlbi, LOGL_DEBUG, "Rx Pkt UL ACK/NACK, stop
T3182\n");
osmo_timer_del(&fi->timer);
fi->T = 0;
}
- if (ctx_ul_ack_nack->final_ack) {
- LOGPFSML(ctx->fi, LOGL_DEBUG, "Final ACK received\n");
- ctx->rx_final_pkt_ul_ack_nack_has_tbf_est = ctx_ul_ack_nack->tbf_est;
+ /* If RRBP contains valid data, schedule a response (PKT CONTROL ACK or PKT RESOURCE
REQ). */
+ if (dlbi->dl_block.SP) {
+ uint32_t poll_fn = rrbp2fn(dlbi->fn, dlbi->dl_block.RRBP);
+ gprs_rlcmac_pdch_ulc_reserve(g_rlcmac_ctx->sched.ulc[dlbi->ts_nr], poll_fn,
+ GPRS_RLCMAC_PDCH_ULC_POLL_UL_ACK,
+ ul_tbf_as_tbf(ctx->ul_tbf));
+ }
+ if (ack_desc->FINAL_ACK_INDICATION) {
+ bool tbf_est = (gprs->Exist_AdditionsR99 &&
gprs->AdditionsR99.TBF_EST);
+ LOGPFSMLDLBI(ctx->fi, dlbi, LOGL_DEBUG, "Final ACK received\n");
+ ctx->rx_final_pkt_ul_ack_nack_has_tbf_est = tbf_est;
tbf_ul_fsm_state_chg(fi, GPRS_RLCMAC_TBF_UL_ST_RELEASING);
}
break;
+ }
case GPRS_RLCMAC_TBF_UL_EV_LAST_UL_DATA_SENT:
/* If LAST_UL_DATA_SENT is received in this state, it means the UL TBF is
retransmitting the block. */
ctx->last_data_block_retrans_attempts++;
diff --git a/tests/rlcmac/rlcmac_prim_test.err b/tests/rlcmac/rlcmac_prim_test.err
index c6c4ebc..366e321 100644
--- a/tests/rlcmac/rlcmac_prim_test.err
+++ b/tests/rlcmac/rlcmac_prim_test.err
@@ -61,9 +61,9 @@
DLGLOBAL DEBUG TBF(UL:NR-0:TLLI-00002342) V(B): (V(A)=2)""(V(S)-1=1) A=Acked
N=Nacked U=Unacked X=Resend-Unacked I=Invalid
DLGLOBAL INFO UL_TBF{FINISHED}: Received Event RX_UL_ACK_NACK
DLGLOBAL INFO UL_TBF{FINISHED}: Contention resolution succeeded, stop T3166
-DLGLOBAL DEBUG UL_TBF{FINISHED}: Final ACK received
-DLGLOBAL INFO UL_TBF{FINISHED}: state_chg to RELEASING
DLGLOBAL DEBUG Register POLL (TS=7 FN=21, reason=UL_ACK)
+DLGLOBAL DEBUG UL_TBF{FINISHED}: (ts=7,fn=8) Final ACK received
+DLGLOBAL INFO UL_TBF{FINISHED}: state_chg to RELEASING
DLGLOBAL DEBUG Rx from lower layers: L1CTL-PDCH_RTS.indication
DLGLOBAL DEBUG Rx RTS.ind (fn=21, ts=7, usf=0)
DLGLOBAL DEBUG (ts=7,fn=21,usf=0) Tx Pkt Control Ack (UL ACK/NACK poll)
@@ -933,9 +933,9 @@
DLGLOBAL DEBUG TBF(UL:NR-0:TLLI-00002342) V(B): (V(A)=1)""(V(S)-1=0) A=Acked
N=Nacked U=Unacked X=Resend-Unacked I=Invalid
DLGLOBAL INFO UL_TBF{FINISHED}: Received Event RX_UL_ACK_NACK
DLGLOBAL INFO UL_TBF{FINISHED}: Contention resolution succeeded, stop T3166
-DLGLOBAL DEBUG UL_TBF{FINISHED}: Final ACK received
-DLGLOBAL INFO UL_TBF{FINISHED}: state_chg to RELEASING
DLGLOBAL DEBUG Register POLL (TS=7 FN=17, reason=UL_ACK)
+DLGLOBAL DEBUG UL_TBF{FINISHED}: (ts=7,fn=4) Final ACK received
+DLGLOBAL INFO UL_TBF{FINISHED}: state_chg to RELEASING
DLGLOBAL INFO Rx from upper layers: GRR-UNITDATA.request
DLGLOBAL DEBUG GRE(00002342) Enqueueing LLC-PDU len=14 SAPI=GMM radio_prio=1
DLGLOBAL DEBUG Rx from lower layers: L1CTL-PDCH_RTS.indication
--
To view, visit
https://gerrit.osmocom.org/c/libosmo-gprs/+/35783?usp=email
To unsubscribe, or for help writing mail filters, visit
https://gerrit.osmocom.org/settings
Gerrit-Project: libosmo-gprs
Gerrit-Branch: master
Gerrit-Change-Id: Iaa8ad8052b9f3b52b05af2b7fc9cb8172f1b6bb7
Gerrit-Change-Number: 35783
Gerrit-PatchSet: 2
Gerrit-Owner: pespin <pespin(a)sysmocom.de>
Gerrit-Reviewer: Jenkins Builder
Gerrit-Reviewer: fixeria <vyanitskiy(a)sysmocom.de>
Gerrit-Reviewer: pespin <pespin(a)sysmocom.de>
Gerrit-MessageType: merged