Change in osmo-pcu[master]: encoding: use CSN.1 codec to generate Packet Uplink Assignment

This is merely a historical archive of years 2008-2021, before the migration to mailman3.

A maintained and still updated list archive can be found at https://lists.osmocom.org/hyperkitty/list/gerrit-log@lists.osmocom.org/.

fixeria gerrit-no-reply at lists.osmocom.org
Tue Sep 8 09:50:54 UTC 2020


fixeria has submitted this change. ( https://gerrit.osmocom.org/c/osmo-pcu/+/19787 )

Change subject: encoding: use CSN.1 codec to generate Packet Uplink Assignment
......................................................................

encoding: use CSN.1 codec to generate Packet Uplink Assignment

It's quite odd to see that in write_packet_downlink_assignment()
we initialize an 'RlcMacDownlink_t', so then the caller can use
the power of CSN.1 codec to generate the final sequence of bytes
to be transmitted, while in write_packet_uplink_assignment() we
already compose the final RLC/MAC message straight away using
the low-level bitvec API (like bitvec_write_field()).

I guess the reason is that at the time of writing this code, the
CSN.1 codec was not stable enough, so it was safer to generate
the message 'by hand'.  This would also explain why we *decode*
the final RLC/MAC message in create_ul_ass() right after encoding.

Rewrite write_packet_uplink_assignment(), so now it initializes
a caller-provided 'RlcMacDownlink_t' structure.  Given that it's
allocated on heap using talloc_zero(), do not initialize presence
indicators of fields that are not present in the message.

This would facilitate handling of frequency hopping parameters
in the upcoming changes, in particular we can now introduce a
function that would compose Frequency Parameters IE for both
write_packet_{downlink,uplink}_assignment().

Tested manually by running a GPRS-enabled network, as well as by
running test cases from ttcn3-pcu-test => no regressions observed.

Change-Id: I2850b91e0043cdca8ae7498a5fc727eeedd029b6
Related: SYS#4868, OS#4547
---
M src/encoding.cpp
M src/encoding.h
M src/tbf.cpp
3 files changed, 108 insertions(+), 78 deletions(-)

Approvals:
  Jenkins Builder: Verified
  laforge: Looks good to me, but someone else must approve
  pespin: Looks good to me, approved



diff --git a/src/encoding.cpp b/src/encoding.cpp
index 2cee251..ef21b61 100644
--- a/src/encoding.cpp
+++ b/src/encoding.cpp
@@ -536,95 +536,125 @@
 	return plen;
 }
 
-/* generate uplink assignment */
+/* Generate Packet Uplink Assignment as per 3GPP TS 44.060, section 11.2.29.
+ * NOTE: 'block' is expected to be zero-initialized by the caller. */
 void Encoding::write_packet_uplink_assignment(
-	bitvec * dest, uint8_t old_tfi,
+	RlcMacDownlink_t * block, uint8_t old_tfi,
 	uint8_t old_downlink, uint32_t tlli, uint8_t use_tlli,
 	const struct gprs_rlcmac_ul_tbf *tbf, uint8_t poll, uint8_t rrbp, uint8_t alpha,
 	uint8_t gamma, int8_t ta_idx, bool use_egprs)
 {
-	// TODO We should use our implementation of encode RLC/MAC Control messages.
-	unsigned wp = 0;
-	uint8_t ts;
-	/* timeslot assigned for the Continuous Timing Advance procedure */
-	uint8_t ta_ts = 0; /* FIXME: supply it as parameter from caller */
+	Packet_Uplink_Assignment_t *pua;
+	Packet_Timing_Advance_t *pta;
+	Frequency_Parameters_t *fp;
+	Dynamic_Allocation_t *da;
 
-	bitvec_write_field(dest, &wp,0x1,2);  // Payload Type
-	bitvec_write_field(dest, &wp,rrbp,2);  // Uplink block with TDMA framenumber (N+13)
-	bitvec_write_field(dest, &wp,poll,1);  // Suppl/Polling Bit
-	bitvec_write_field(dest, &wp,0x0,3);  // Uplink state flag
-	bitvec_write_field(dest, &wp,0xa,6);  // MESSAGE TYPE
+	/* RLC/MAC control block without the optional RLC/MAC control header */
+	block->PAYLOAD_TYPE = 0x01;  // Payload Type
+	block->RRBP         = rrbp;  // RRBP (e.g. N+13)
+	block->SP           = poll;  // RRBP field is valid
+	block->USF          = 0x00;  // Uplink state flag
 
-	bitvec_write_field(dest, &wp,0x0,2);  // Page Mode
+	/* See 3GPP TS 44.060, section 11.2.29 */
+	pua = &block->u.Packet_Uplink_Assignment;
+	pua->MESSAGE_TYPE = 0x0a;  // Packet Uplink Assignment
+	pua->PAGE_MODE    = 0x00;  // Normal Paging
 
-	bitvec_write_field(dest, &wp,0x0,1); // switch PERSIST_LEVEL: off
+	/* TLLI or Global (UL/DL) TFI */
 	if (use_tlli) {
-		bitvec_write_field(dest, &wp,0x2,2); // switch TLLI   : on
-		bitvec_write_field(dest, &wp,tlli,32); // TLLI
+		pua->ID.UnionType = 0x01;
+		pua->ID.u.TLLI = tlli;
 	} else {
-		bitvec_write_field(dest, &wp,0x0,1); // switch TFI : on
-		bitvec_write_field(dest, &wp,old_downlink,1); // 0=UPLINK TFI, 1=DL TFI
-		bitvec_write_field(dest, &wp,old_tfi,5); // TFI
+		pua->ID.UnionType = 0x00;
+		pua->ID.u.Global_TFI.UnionType = old_downlink;
+		pua->ID.u.Global_TFI.u.UPLINK_TFI = old_tfi;
 	}
 
+	/* GPRS/EGPRS specific parameters */
+	pua->UnionType = use_egprs ? 0x01 : 0x00;
 	if (!use_egprs) {
-		bitvec_write_field(dest, &wp,0x0,1); // Message escape
-		bitvec_write_field(dest, &wp, mcs_chan_code(tbf->current_cs()), 2); // CHANNEL_CODING_COMMAND
-		bitvec_write_field(dest, &wp,0x1,1); // TLLI_BLOCK_CHANNEL_CODING
-		write_ta_ie(dest, wp, tbf->ta(), ta_idx, ta_ts);
-	} else { /* EPGRS */
-		bitvec_write_field(dest, &wp,0x1,1); // Message escape
-		bitvec_write_field(dest, &wp,0x0,2); // EGPRS message contents
-		bitvec_write_field(dest, &wp,0x0,1); // No CONTENTION_RESOLUTION_TLLI
-		bitvec_write_field(dest, &wp,0x0,1); // No COMPACT reduced MA
-		bitvec_write_field(dest, &wp, mcs_chan_code(tbf->current_cs()), 4); // EGPRS Modulation and Coding IE
-		/* 0: no RESEGMENT, 1: Segmentation*/
-		bitvec_write_field(dest, &wp, 0x1, 1);
-		write_ws(dest, &wp, tbf->window_size()); // EGPRS Window Size
-		bitvec_write_field(dest, &wp,0x0,1); // No Access Technologies Request
-		bitvec_write_field(dest, &wp,0x0,1); // No ARAC RETRANSMISSION REQUEST
-		bitvec_write_field(dest, &wp,0x1,1); // TLLI_BLOCK_CHANNEL_CODING
-		bitvec_write_field(dest, &wp,0x0,1); // No BEP_PERIOD2
-		write_ta_ie(dest, wp, tbf->ta(), ta_idx, ta_ts);
-		bitvec_write_field(dest, &wp,0x0,1); // No Packet Extended Timing Advance
+		PUA_GPRS_t *gprs = &pua->u.PUA_GPRS_Struct;
+
+		/* Use the commanded CS/MSC value during the content resolution */
+		gprs->CHANNEL_CODING_COMMAND    = mcs_chan_code(tbf->current_cs());
+		gprs->TLLI_BLOCK_CHANNEL_CODING = 0x01;  // ^^^
+
+		/* Dynamic allocation */
+		gprs->UnionType = 0x01;
+		/* Frequency Parameters IE is present */
+		gprs->Exist_Frequency_Parameters = 0x01;
+
+		/* Common parameters to be set below */
+		pta = &gprs->Packet_Timing_Advance;
+		fp = &gprs->Frequency_Parameters;
+		da = &gprs->u.Dynamic_Allocation;
+	} else {
+		PUA_EGPRS_00_t *egprs = &pua->u.PUA_EGPRS_Struct.u.PUA_EGPRS_00;
+		pua->u.PUA_EGPRS_Struct.UnionType = 0x00;  // 'Normal' EGPRS, not EGPRS2
+
+		/* Use the commanded CS/MSC value during the content resolution */
+		egprs->EGPRS_CHANNEL_CODING_COMMAND = mcs_chan_code(tbf->current_cs());
+		egprs->TLLI_BLOCK_CHANNEL_CODING    = 0x01;  // ^^^
+		egprs->RESEGMENT                    = 0x01;  // Enable segmentation
+		egprs->EGPRS_WindowSize             = tbf->window_size();
+
+		/* Dynamic allocation */
+		egprs->UnionType = 0x01;
+		/* Frequency Parameters IE is present */
+		egprs->Exist_Frequency_Parameters = 0x01;
+
+		/* Common parameters to be set below */
+		pta = &egprs->Packet_Timing_Advance;
+		fp = &egprs->Frequency_Parameters;
+		da = &egprs->u.Dynamic_Allocation;
 	}
 
-#if 1
-	bitvec_write_field(dest, &wp,0x1,1); // Frequency Parameters information elements = present
-	bitvec_write_field(dest, &wp,tbf->tsc(),3); // Training Sequence Code (TSC)
-	bitvec_write_field(dest, &wp,0x0,2); // ARFCN = present
-	bitvec_write_field(dest, &wp,tbf->trx->arfcn,10); // ARFCN
-#else
-	bitvec_write_field(dest, &wp,0x0,1); // Frequency Parameters = off
-#endif
-
-	bitvec_write_field(dest, &wp,0x1,2); // Dynamic Allocation
-
-	bitvec_write_field(dest, &wp,0x0,1); // Extended Dynamic Allocation = off
-	bitvec_write_field(dest, &wp,0x0,1); // P0 = off
-
-	bitvec_write_field(dest, &wp,0x0,1); // USF_GRANULARITY
-	bitvec_write_field(dest, &wp,0x1,1); // switch TFI   : on
-	bitvec_write_field(dest, &wp,tbf->tfi(),5);// TFI
-
-	bitvec_write_field(dest, &wp,0x0,1); //
-	bitvec_write_field(dest, &wp,0x0,1); // TBF Starting Time = off
-	if (alpha || gamma) {
-		bitvec_write_field(dest, &wp,0x1,1); // Timeslot Allocation with Power Control
-		bitvec_write_field(dest, &wp,alpha,4);   // ALPHA
-	} else
-		bitvec_write_field(dest, &wp,0x0,1); // Timeslot Allocation
-
-	for (ts = 0; ts < 8; ts++) {
-		if (tbf->pdch[ts]) {
-			bitvec_write_field(dest, &wp,0x1,1); // USF_TN(i): on
-			bitvec_write_field(dest, &wp,tbf->m_usf[ts],3); // USF_TN(i)
-			if (alpha || gamma)
-				bitvec_write_field(dest, &wp,gamma,5);   // GAMMA power control parameter
-		} else
-			bitvec_write_field(dest, &wp,0x0,1); // USF_TN(i): off
+	/* Packet Timing Advance (if known) */
+	if (tbf->ta() <= 63) { /* { 0 | 1  < TIMING_ADVANCE_VALUE : bit (6) > } */
+		pta->Exist_TIMING_ADVANCE_VALUE = 0x01;  // Present
+		pta->TIMING_ADVANCE_VALUE       = tbf->ta();
 	}
-	//	bitvec_write_field(dest, &wp,0x0,1); // Measurement Mapping struct not present
+
+	/* Continuous Timing Advance Control */
+	if (ta_idx >= 0 && ta_idx < 16) {
+		pta->Exist_IndexAndtimeSlot         = 0x01;  // Present
+		pta->TIMING_ADVANCE_TIMESLOT_NUMBER = 0;  // FIXME!
+		pta->TIMING_ADVANCE_INDEX           = ta_idx;
+	}
+
+	/* Frequency Parameters IE */
+	fp->TSC       = tbf->tsc();  // Training Sequence Code (TSC)
+	fp->UnionType = 0x00;        // Single ARFCN
+	fp->u.ARFCN   = tbf->trx->arfcn;
+
+	/* Dynamic allocation parameters */
+	da->USF_GRANULARITY = 0x00;
+
+	/* Assign an Uplink TFI */
+	da->Exist_UPLINK_TFI_ASSIGNMENT = 0x01;
+	da->UPLINK_TFI_ASSIGNMENT = tbf->tfi();
+
+	/* Timeslot Allocation with or without Power Control */
+	da->UnionType = (alpha || gamma) ? 0x01 : 0x00;
+	if (da->UnionType == 0x01)
+		da->u.Timeslot_Allocation_Power_Ctrl_Param.ALPHA = alpha;
+
+	for (unsigned int tn = 0; tn < 8; tn++) {
+		if (tbf->pdch[tn] == NULL)
+			continue;
+
+		if (da->UnionType == 0x01) {
+			Timeslot_Allocation_Power_Ctrl_Param_t *params = \
+				&da->u.Timeslot_Allocation_Power_Ctrl_Param;
+			params->Slot[tn].Exist    = 0x01;  // Enable this timeslot
+			params->Slot[tn].USF_TN   = tbf->m_usf[tn];  // USF_TN(i)
+			params->Slot[tn].GAMMA_TN = gamma;
+		} else {
+			Timeslot_Allocation_t *slot = &da->u.Timeslot_Allocation[tn];
+			slot->Exist  = 0x01;  // Enable this timeslot
+			slot->USF_TN = tbf->m_usf[tn];  // USF_TN(i)
+		}
+	}
 }
 
 
diff --git a/src/encoding.h b/src/encoding.h
index 18392f7..5f8496e 100644
--- a/src/encoding.h
+++ b/src/encoding.h
@@ -58,7 +58,7 @@
 		);
 
 	static void write_packet_uplink_assignment(
-			bitvec * dest, uint8_t old_tfi,
+			RlcMacDownlink_t * block, uint8_t old_tfi,
 			uint8_t old_downlink, uint32_t tlli, uint8_t use_tlli,
 			const struct gprs_rlcmac_ul_tbf *tbf, uint8_t poll, uint8_t rrbp,
 			uint8_t alpha, uint8_t gamma, int8_t ta_idx,
diff --git a/src/tbf.cpp b/src/tbf.cpp
index c1ec729..0447edc 100644
--- a/src/tbf.cpp
+++ b/src/tbf.cpp
@@ -1368,16 +1368,16 @@
 	bitvec_unhex(&bv, DUMMY_VEC);
 
 	LOGPTBF(new_tbf, LOGL_INFO, "start Packet Uplink Assignment (PACCH)\n");
-	Encoding::write_packet_uplink_assignment(&bv, m_tfi,
+	mac_control_block = (RlcMacDownlink_t *)talloc_zero(tall_pcu_ctx, RlcMacDownlink_t);
+	Encoding::write_packet_uplink_assignment(mac_control_block, m_tfi,
 		(direction == GPRS_RLCMAC_DL_TBF), tlli(),
 		is_tlli_valid(), new_tbf, 1, rrbp, bts_data()->alpha,
 		bts_data()->gamma, -1, is_egprs_enabled());
 
-	mac_control_block = (RlcMacDownlink_t *)talloc_zero(tall_pcu_ctx, RlcMacDownlink_t);
 	LOGP(DTBF, LOGL_DEBUG, "+++++++++++++++++++++++++ TX : Packet Uplink Assignment +++++++++++++++++++++++++\n");
-	rc = decode_gsm_rlcmac_downlink(&bv, mac_control_block);
+	rc = encode_gsm_rlcmac_downlink(&bv, mac_control_block);
 	if (rc < 0) {
-		LOGP(DTBF, LOGL_ERROR, "Decoding of Packet Uplink Ass failed (%d)\n", rc);
+		LOGP(DTBF, LOGL_ERROR, "Encoding of Packet Uplink Ass failed (%d)\n", rc);
 		goto free_ret;
 	}
 	LOGP(DTBF, LOGL_DEBUG, "------------------------- TX : Packet Uplink Assignment -------------------------\n");

-- 
To view, visit https://gerrit.osmocom.org/c/osmo-pcu/+/19787
To unsubscribe, or for help writing mail filters, visit https://gerrit.osmocom.org/settings

Gerrit-Project: osmo-pcu
Gerrit-Branch: master
Gerrit-Change-Id: I2850b91e0043cdca8ae7498a5fc727eeedd029b6
Gerrit-Change-Number: 19787
Gerrit-PatchSet: 4
Gerrit-Owner: fixeria <vyanitskiy at sysmocom.de>
Gerrit-Reviewer: Jenkins Builder
Gerrit-Reviewer: fixeria <vyanitskiy at sysmocom.de>
Gerrit-Reviewer: laforge <laforge at osmocom.org>
Gerrit-Reviewer: pespin <pespin at sysmocom.de>
Gerrit-MessageType: merged
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.osmocom.org/pipermail/gerrit-log/attachments/20200908/024d79ce/attachment.htm>


More information about the gerrit-log mailing list