aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorJacob Erlbeck <jerlbeck@sysmocom.de>2015-09-28 17:55:32 +0200
committerJacob Erlbeck <jerlbeck@sysmocom.de>2015-11-30 12:20:36 +0100
commitc3c58046c7223d48c61eb7126f33dca300254485 (patch)
tree6c28490d15cc70d5a0774a3c7fd56e645bf2ae50
parent111ebe84c2b0a49472ec59022aecf56adfefd82e (diff)
edge: Get EGPRS multislot class
The EGPRS MS class ist contained in the MS_RA_capability information. Its presence indicates, that the MS is able (and willing) to use EGPRS. This commit implements basic support for retrieving, storing, and showing it in the VTY. The information is stored in the MS object. Sponsored-by: On-Waves ehf
-rw-r--r--src/bts.cpp18
-rw-r--r--src/decoding.cpp15
-rw-r--r--src/decoding.h1
-rw-r--r--src/gprs_ms.cpp13
-rw-r--r--src/gprs_ms.h8
-rw-r--r--src/pcu_vty_functions.cpp1
6 files changed, 54 insertions, 2 deletions
diff --git a/src/bts.cpp b/src/bts.cpp
index edae7371..26077c21 100644
--- a/src/bts.cpp
+++ b/src/bts.cpp
@@ -990,6 +990,7 @@ void gprs_rlcmac_pdch::rcv_resource_request(Packet_Resource_Request_t *request,
struct gprs_rlcmac_dl_tbf *dl_tbf = NULL;
uint32_t tlli = request->ID.u.TLLI;
uint8_t ms_class = 0;
+ uint8_t egprs_ms_class = 0;
uint8_t ta = 0;
struct pcu_l1_meas meas;
@@ -1039,10 +1040,19 @@ void gprs_rlcmac_pdch::rcv_resource_request(Packet_Resource_Request_t *request,
ta = sba->ta;
bts()->sba()->free_sba(sba);
}
- if (request->Exist_MS_Radio_Access_capability)
- ms_class = Decoding::get_ms_class_by_capability(&request->MS_Radio_Access_capability);
+ if (request->Exist_MS_Radio_Access_capability) {
+ ms_class = Decoding::get_ms_class_by_capability(
+ &request->MS_Radio_Access_capability);
+ egprs_ms_class =
+ Decoding::get_egprs_ms_class_by_capability(
+ &request->MS_Radio_Access_capability);
+ }
if (!ms_class)
LOGP(DRLCMAC, LOGL_NOTICE, "MS does not give us a class.\n");
+ if (egprs_ms_class)
+ LOGP(DRLCMAC, LOGL_NOTICE,
+ "MS supports EGPRS multislot class %d.\n",
+ egprs_ms_class);
ul_tbf = tbf_alloc_ul(bts_data(), trx_no(), ms_class, tlli, ta, ms);
if (!ul_tbf)
return;
@@ -1053,6 +1063,10 @@ void gprs_rlcmac_pdch::rcv_resource_request(Packet_Resource_Request_t *request,
/* schedule uplink assignment */
ul_tbf->ul_ass_state = GPRS_RLCMAC_UL_ASS_SEND_ASS;
+ /* get capabilities */
+ if (ul_tbf->ms())
+ ul_tbf->ms()->set_egprs_ms_class(egprs_ms_class);
+
/* get measurements */
if (ul_tbf->ms()) {
get_meas(&meas, request);
diff --git a/src/decoding.cpp b/src/decoding.cpp
index fce8124f..d4f014b2 100644
--- a/src/decoding.cpp
+++ b/src/decoding.cpp
@@ -83,6 +83,21 @@ uint8_t Decoding::get_ms_class_by_capability(MS_Radio_Access_capability_t *cap)
return 0;
}
+uint8_t Decoding::get_egprs_ms_class_by_capability(MS_Radio_Access_capability_t *cap)
+{
+ int i;
+
+ for (i = 0; i < cap->Count_MS_RA_capability_value; i++) {
+ if (!cap->MS_RA_capability_value[i].u.Content.Exist_Multislot_capability)
+ continue;
+ if (!cap->MS_RA_capability_value[i].u.Content.Multislot_capability.Exist_EGPRS_multislot_class)
+ continue;
+ return cap->MS_RA_capability_value[i].u.Content.Multislot_capability.EGPRS_multislot_class;
+ }
+
+ return 0;
+}
+
/**
* show_rbb needs to be an array with 65 elements
* The index of the array is the bit position in the rbb
diff --git a/src/decoding.h b/src/decoding.h
index 31be0320..03dad47e 100644
--- a/src/decoding.h
+++ b/src/decoding.h
@@ -28,6 +28,7 @@ public:
static int tlli_from_ul_data(const uint8_t *data, uint8_t len,
uint32_t *tlli);
static uint8_t get_ms_class_by_capability(MS_Radio_Access_capability_t *cap);
+ static uint8_t get_egprs_ms_class_by_capability(MS_Radio_Access_capability_t *cap);
static void extract_rbb(const uint8_t *rbb, char *extracted_rbb);
};
diff --git a/src/gprs_ms.cpp b/src/gprs_ms.cpp
index 807f3459..76fe47c2 100644
--- a/src/gprs_ms.cpp
+++ b/src/gprs_ms.cpp
@@ -96,6 +96,7 @@ GprsMs::GprsMs(BTS *bts, uint32_t tlli) :
m_new_dl_tlli(0),
m_ta(0),
m_ms_class(0),
+ m_egprs_ms_class(0),
m_current_cs_ul(1),
m_current_cs_dl(1),
m_is_idle(true),
@@ -447,6 +448,18 @@ void GprsMs::set_ms_class(uint8_t ms_class_)
m_ms_class = ms_class_;
}
+void GprsMs::set_egprs_ms_class(uint8_t ms_class_)
+{
+ if (ms_class_ == m_egprs_ms_class)
+ return;
+
+ LOGP(DRLCMAC, LOGL_INFO,
+ "Modifying MS object, TLLI = 0x%08x, EGPRS MS class %d -> %d\n",
+ tlli(), m_egprs_ms_class, ms_class_);
+
+ m_egprs_ms_class = ms_class_;
+}
+
void GprsMs::update_error_rate(gprs_rlcmac_tbf *tbf, int error_rate)
{
struct gprs_rlcmac_bts *bts_data;
diff --git a/src/gprs_ms.h b/src/gprs_ms.h
index e820e196..f9b63f26 100644
--- a/src/gprs_ms.h
+++ b/src/gprs_ms.h
@@ -81,7 +81,9 @@ public:
uint8_t ta() const;
void set_ta(uint8_t ta);
uint8_t ms_class() const;
+ uint8_t egprs_ms_class() const;
void set_ms_class(uint8_t ms_class);
+ void set_egprs_ms_class(uint8_t ms_class);
uint8_t current_cs_ul() const;
uint8_t current_cs_dl() const;
@@ -148,6 +150,7 @@ private:
char m_imsi[16];
uint8_t m_ta;
uint8_t m_ms_class;
+ uint8_t m_egprs_ms_class;
/* current coding scheme */
uint8_t m_current_cs_ul;
uint8_t m_current_cs_dl;
@@ -212,6 +215,11 @@ inline uint8_t GprsMs::ms_class() const
return m_ms_class;
}
+inline uint8_t GprsMs::egprs_ms_class() const
+{
+ return m_egprs_ms_class;
+}
+
inline uint8_t GprsMs::current_cs_ul() const
{
return m_current_cs_ul;
diff --git a/src/pcu_vty_functions.cpp b/src/pcu_vty_functions.cpp
index d2a3641a..ce2a006a 100644
--- a/src/pcu_vty_functions.cpp
+++ b/src/pcu_vty_functions.cpp
@@ -70,6 +70,7 @@ static int show_ms(struct vty *vty, GprsMs *ms)
vty_out(vty, " Coding scheme downlink: CS-%d%s", ms->current_cs_dl(),
VTY_NEWLINE);
vty_out(vty, " MS class: %d%s", ms->ms_class(), VTY_NEWLINE);
+ vty_out(vty, " EGPRS MS class: %d%s", ms->egprs_ms_class(), VTY_NEWLINE);
vty_out(vty, " LLC queue length: %d%s", ms->llc_queue()->size(),
VTY_NEWLINE);
vty_out(vty, " LLC queue octets: %d%s", ms->llc_queue()->octets(),