This patch includes the changes for encoding of PUAN to
handle the CRBB bitmap
---
src/encoding.cpp | 103 ++++++++++++++++++++++++++++++++++++++++++------------
src/rlc.cpp | 28 +++++++++++++++
src/rlc.h | 1 +
3 files changed, 109 insertions(+), 23 deletions(-)
diff --git a/src/encoding.cpp b/src/encoding.cpp
index 6c50abe..e0c29af 100644
--- a/src/encoding.cpp
+++ b/src/encoding.cpp
@@ -25,6 +25,11 @@
#include <tbf.h>
#include <gprs_debug.h>
+extern "C" {
+#include <osmocom/core/utils.h>
+#include <osmocom/core/bitcomp.h>
+}
+
#include <errno.h>
#include <string.h>
@@ -537,8 +542,6 @@ static void write_packet_ack_nack_desc_egprs(
gprs_rlc_ul_window *window, bool is_final)
{
int urbb_len = 0;
- int crbb_len = 0;
- int len;
bool bow = true;
bool eow = true;
int ssn = window->mod_sns(window->v_q() + 1);
@@ -546,9 +549,55 @@ static void write_packet_ack_nack_desc_egprs(
int esn_crbb = window->mod_sns(ssn - 1);
int rest_bits = dest->data_len * 8 - wp;
- if (num_blocks > 0)
+ uint8_t rbb[128] = {'\0'};
+ uint8_t iter = 0;
+ uint8_t crbb_len = 0;
+ uint8_t len = 0;
+ int is_compressed = 0;
+ uint16_t ucmp_bmplan = window->update_egprs_rbb(rbb);
+ uint8_t crbb_bitmap[127];
+ bool bitmap_len = 0;
+
+ LOGP(DRLCMACUL, LOGL_DEBUG, "Uncompressed bitmap length after"
+ "rbb update %d\n", ucmp_bmplan);
+
+ rbb[128] = 0;
+ bitvec out;
+
+ out.data = rbb;
+ out.cur_bit = 0;
+ out.data_len = sizeof(rbb);
+ /* if [V(R) -1] modulo SNS is explicitly included in the bitmap,
+ set eow =1;
+
+ * If V(Q) equals V(R), then BOW and EOW bit shall be set to the value '1'
+ * and no need to send bitmap in ack nack, hence no compression
+ */
+ if (window->v_q() == window->v_r()) {
+
+ LOGP(DRLCMACUL, LOGL_DEBUG, "write_packet_ack_nack_desc_egprs:"
+ "v(Q)=V(R), hence no compression"
+ " %d %d\n", window->v_q(), window->v_r());
+ eow = bow = 1;
+ bitmap_len = 1;
+ }
+ /* Compression part, Try compression only if it is greater than or equal
+ * to Window size Otherwise encode it in uncompressed
+ */
+ if ((ucmp_bmplan >= (rest_bits - 15)) && (!bitmap_len)) {
+
+ is_compressed = osmo_bitmap_compress(&out, //Uncompressed bitmap
+ &ucmp_bmplan, //Uncompressed bitmap len
+ &crbb_len, //Compressed bitmap len
+ crbb_bitmap
+ );
+ }
+
+ if (num_blocks > 0) {
/* V(Q) is NACK and omitted -> SSN = V(Q) + 1 */
num_blocks -= 1;
+ urbb_len = num_blocks;
+ }
if (num_blocks > window->ws())
num_blocks = window->ws();
@@ -556,17 +605,10 @@ static void write_packet_ack_nack_desc_egprs(
if (num_blocks > rest_bits) {
eow = false;
urbb_len = rest_bits;
- /* TODO: use compression, start encoding bits and stop when the
- * space is exhausted. Use the first combination that encodes
- * all bits. If there is none, use the combination that encodes
- * the largest number of bits (e.g. by setting num_blocks to the
- * max and repeating the construction).
- */
} else if (num_blocks > rest_bits - 9) {
/* union bit and length field take 9 bits */
eow = false;
urbb_len = rest_bits - 9;
- /* TODO: use compression (see above) */
}
if (urbb_len + crbb_len == rest_bits)
@@ -588,20 +630,35 @@ static void write_packet_ack_nack_desc_egprs(
bitvec_write_field(dest, wp, bow, 1); // BEGINNING_OF_WINDOW
bitvec_write_field(dest, wp, eow, 1); // END_OF_WINDOW
bitvec_write_field(dest, wp, ssn, 11); // STARTING_SEQUENCE_NUMBER
- bitvec_write_field(dest, wp, 0, 1); // 0: don't have CRBB
- /* TODO: Add CRBB support */
-
- LOGP(DRLCMACUL, LOGL_DEBUG,
- " - EGPRS URBB, len = %d, SSN = %d, ESN_CRBB = %d, "
- "SNS = %d, WS = %d, V(Q) = %d, V(R) = %d%s%s\n",
- urbb_len, ssn, esn_crbb,
- window->sns(), window->ws(), window->v_q(), window->v_r(),
- bow ? ", BOW" : "", eow ? ", EOW" : "");
- for (int i = urbb_len; i > 0; i--) {
- /* Set bit at the appropriate position (see 3GPP TS 04.60 12.3.1) */
- bool is_ack = window->m_v_n.is_received(esn_crbb + i);
- bitvec_write_field(dest, wp, is_ack, 1);
+ if (is_compressed) {
+ bitvec_write_field(dest, wp, 1, 1); // CRBB_Exist
+ bitvec_write_field(dest, wp, crbb_len, 7); // CRBB_LENGTH
+ uint8_t crbb_start_clr_code = (0x80 & crbb_bitmap[0])>>7;
+ bitvec_write_field(dest, wp, crbb_start_clr_code, 1); // CRBB_clr_code
+
+ while (crbb_len != 0) {
+ if (crbb_len > 8) {
+ bitvec_write_field(dest, wp, crbb_bitmap[iter], 8);
+ crbb_len = crbb_len - 8;
+ iter++;
+ } else{
+ bitvec_write_field(dest, wp, crbb_bitmap[iter], crbb_len);
+ crbb_len = 0;
+ }
+ }
+ } else{
+ LOGP(DRLCMACUL, LOGL_DEBUG,
+ " - EGPRS URBB, len = %d, SSN = %d, ESN_CRBB = %d, "
+ "SNS = %d, WS = %d, V(Q) = %d, V(R) = %d%s%s\n",
+ urbb_len, ssn, esn_crbb,
+ window->sns(), window->ws(), window->v_q(), window->v_r(),
+ bow ? ", BOW" : "", eow ? ", EOW" : "");
+ for (int i = urbb_len; i > 0; i--) {
+ /* Set bit at the appropriate position (see 3GPP TS 04.60 12.3.1) */
+ bool is_ack = window->m_v_n.is_received(esn_crbb + i);
+ bitvec_write_field(dest, wp, is_ack, 1);
+ }
}
}
diff --git a/src/rlc.cpp b/src/rlc.cpp
index 6770043..c201713 100644
--- a/src/rlc.cpp
+++ b/src/rlc.cpp
@@ -83,6 +83,34 @@ int gprs_rlc_dl_window::mark_for_resend()
return resend;
}
+/* Update the receive block bitmap */
+uint16_t gprs_rlc_ul_window::update_egprs_rbb(uint8_t *rbb)
+{
+ int i;
+ uint16_t bsn;
+ int8_t bitmask = 0x80;
+ int8_t pos = 0;
+ int8_t bit_pos = 0;
+ for (i = 0, bsn = (v_q()+1); ((bsn < (v_r())) && (i < ws())); i++,
+ bsn = this->mod_sns(bsn + 1)) {
+ if (m_v_n.is_received(bsn)) {
+ rbb[pos] = rbb[pos] | bitmask;
+ } else {
+ rbb[pos] = rbb[pos] & (~bitmask);
+ }
+ bitmask = bitmask >> 1;
+ bit_pos++;
+ bit_pos = bit_pos % 8;
+ if(bit_pos == 0) {
+ pos++;
+ bitmask = 0x80;
+ }
+ }
+ LOGP(DRLCMACUL, LOGL_DEBUG, "V(N):in update_egprs_rbb \"%s\""
+ "R=Received I=Invalid\n", rbb);
+ return i;
+}
+
int gprs_rlc_dl_window::count_unacked()
{
uint16_t unacked = 0;
diff --git a/src/rlc.h b/src/rlc.h
index 8f75588..83bc5dc 100644
--- a/src/rlc.h
+++ b/src/rlc.h
@@ -260,6 +260,7 @@ struct gprs_rlc_ul_window: public gprs_rlc_window {
bool is_received(uint16_t bsn) const;
void update_rbb(char *rbb);
+ uint16_t update_egprs_rbb(uint8_t *rbb);
void raise_v_r_to(int moves);
void raise_v_r(const uint16_t bsn);
uint16_t raise_v_q();
--
1.7.9.5