aboutsummaryrefslogtreecommitdiffstats
path: root/tests/gad
diff options
context:
space:
mode:
authorNeels Hofmeyr <neels@hofmeyr.de>2020-09-18 18:00:50 +0200
committerNeels Hofmeyr <neels@hofmeyr.de>2020-10-07 11:39:46 +0000
commit086bd33f18fa79eb239a06e404915f3ba3c20e3f (patch)
tree9c808d123c773b3d13d7fe9fc82121ddefafce29 /tests/gad
parent87c3afb5a969838446433c6d0d0ece8e9821e2c0 (diff)
add GAD coding for Location Services
GAD, Universal Geographical Area Description: - raw coding for all GAD elements. - SI-units encoding and decoding for Ellipsoid point with uncertainty circle, which I presume is the typical "at most N meters away from cell tower located at X,Y", which corresponds to the TA positioning currently being implemented. - other SI-units GAD element encodings are so far not implemented. Add encoding and decoding tests. In gsm/protocol/gsm_23_032.h are the raw coding structs as defined in 3GPP TS 23.032. In gsm/gad.h are structs carrying consistent units based on meters and degrees, for convenient / less error prone handling of GAD data, and for human readable representations of the GAD data. The separation of the two is desirable because OsmoBSC will receive GAD data from OsmoSMLC on the Lb interface, and pass on this data to the MSC via the A interface. It is better to pass the GAD data as-is without de/encoding. Change-Id: I7a9dd805a91b1ebb6353bde0cd169218acbf223c
Diffstat (limited to 'tests/gad')
-rw-r--r--tests/gad/gad_test.c143
-rw-r--r--tests/gad/gad_test.ok8
2 files changed, 151 insertions, 0 deletions
diff --git a/tests/gad/gad_test.c b/tests/gad/gad_test.c
new file mode 100644
index 00000000..ca8c4fa8
--- /dev/null
+++ b/tests/gad/gad_test.c
@@ -0,0 +1,143 @@
+#include <stdio.h>
+
+#include <osmocom/core/utils.h>
+#include <osmocom/core/msgb.h>
+#include <osmocom/gsm/gad.h>
+
+void test_gad_lat_lon_dec_enc_stability()
+{
+ uint32_t lat_enc;
+ uint32_t lon_enc;
+ printf("--- %s\n", __func__);
+ for (lat_enc = 0x0; lat_enc <= 0xffffff; lat_enc++) {
+ int32_t lat_dec = osmo_gad_dec_lat(lat_enc);
+ uint32_t enc2 = osmo_gad_enc_lat(lat_dec);
+ uint32_t want_enc = lat_enc;
+ /* "-0" == 0, because the highest bit is defined as a sign bit. */
+ if (lat_enc == 0x800000)
+ want_enc = 0;
+ if (enc2 != want_enc) {
+ printf("ERR: lat=%u --> %d --> %u\n", lat_enc, lat_dec, enc2);
+ printf("%d -> %u\n", lat_dec + 1, osmo_gad_enc_lat(lat_dec + 1));
+ OSMO_ASSERT(false);
+ }
+ }
+ printf("osmo_gad_dec_lat() -> osmo_gad_enc_lat() of %u values successful\n", lat_enc);
+ for (lon_enc = 0; lon_enc <= 0xffffff; lon_enc++) {
+ int32_t lon_dec = osmo_gad_dec_lon(lon_enc);
+ uint32_t enc2 = osmo_gad_enc_lon(lon_dec);
+ uint32_t want_enc = lon_enc;
+ if (enc2 != want_enc) {
+ printf("ERR: lon=%u 0x%x --> %d --> %u\n", lon_enc, lon_enc, lon_dec, enc2);
+ printf("%d -> %u\n", lon_dec + 1, osmo_gad_enc_lon(lon_dec + 1));
+ printf("%d -> %u\n", lon_dec - 1, osmo_gad_enc_lon(lon_dec - 1));
+ OSMO_ASSERT(false);
+ }
+ }
+ printf("osmo_gad_dec_lon() -> osmo_gad_enc_lon() of %u values successful\n", lon_enc);
+}
+
+struct osmo_gad gad_test_values[] = {
+ {
+ .type = GAD_TYPE_ELL_POINT_UNC_CIRCLE,
+ .ell_point_unc_circle = {
+ /* Values rounded to the nearest encodable value, for test result matching */
+ .lat = 23000006,
+ .lon = 42000002,
+ .unc = 442592,
+ },
+ },
+};
+
+void test_gad_enc_dec()
+{
+ int i;
+ printf("--- %s\n", __func__);
+
+ for (i = 0; i < ARRAY_SIZE(gad_test_values); i++) {
+ struct osmo_gad *t = &gad_test_values[i];
+ struct msgb *msg = msgb_alloc(1024, __func__);
+ union gad_raw raw_write;
+ union gad_raw raw_read;
+ struct osmo_gad dec_pdu;
+ int rc;
+ struct osmo_gad_err *err;
+ void *loop_ctx = msg;
+ rc = osmo_gad_enc(&raw_write, t);
+ if (rc <= 0) {
+ printf("[%d] %s: ERROR: osmo_gad_enc() failed\n", i, osmo_gad_type_name(t->type));
+ goto loop_end;
+ }
+ rc = osmo_gad_raw_write(msg, &raw_write);
+ if (rc <= 0) {
+ printf("[%d] %s: ERROR: osmo_gad_raw_write() failed\n", i, osmo_gad_type_name(t->type));
+ goto loop_end;
+ }
+ if (rc != msg->len) {
+ printf("[%d] %s: ERROR: osmo_gad_raw_write() returned length %d but msgb has %d bytes\n",
+ i, osmo_gad_type_name(t->type),
+ rc, msg->len);
+ goto loop_end;
+ }
+
+ memset(&raw_read, 0xff, sizeof(raw_read));
+ rc = osmo_gad_raw_read(&raw_read, &err, loop_ctx, msg->data, msg->len);
+ if (rc) {
+ printf("[%d] ERROR: osmo_gad_raw_read() failed: %s\n", i, err->logmsg);
+ printf(" encoded data: %s\n", osmo_hexdump(msg->data, msg->len));
+ goto loop_end;
+ }
+
+ memset(&dec_pdu, 0xff, sizeof(dec_pdu));
+ rc = osmo_gad_dec(&dec_pdu, &err, loop_ctx, &raw_read);
+ if (rc) {
+ printf("[%d] ERROR: failed to decode pdu: %s\n", i, err->logmsg);
+ printf(" encoded data: %s\n", osmo_hexdump(msg->data, msg->len));
+ goto loop_end;
+ }
+
+ if (memcmp(t, &dec_pdu, sizeof(dec_pdu))) {
+ char strbuf[128];
+ printf("[%d] %s: ERROR: decoded PDU != encoded PDU\n", i,
+ osmo_gad_type_name(t->type));
+ osmo_gad_to_str_buf(strbuf, sizeof(strbuf), t);
+ printf(" original struct: %s\n", strbuf);
+ osmo_gad_to_str_buf(strbuf, sizeof(strbuf), &dec_pdu);
+ printf(" decoded struct: %s\n", strbuf);
+ goto loop_end;
+ }
+
+ printf("[%d] %s: ok\n", i, osmo_gad_type_name(t->type));
+ printf(" encoded data: %s\n", msgb_hexdump(msg));
+
+loop_end:
+ msgb_free(msg);
+ }
+}
+
+void test_gad_to_str()
+{
+ int i;
+ printf("--- %s\n", __func__);
+
+ for (i = 0; i < ARRAY_SIZE(gad_test_values); i++) {
+ struct osmo_gad *t = &gad_test_values[i];
+ char buf[1024];
+ int rc;
+ rc = osmo_gad_to_str_buf(buf, sizeof(buf), t);
+
+ printf("[%d] ", i);
+ if (rc <= 0)
+ printf("%s: ERROR: osmo_gad_to_str_buf() failed\n", osmo_gad_type_name(t->type));
+ else
+ printf("%s\n", buf);
+ }
+}
+
+int main()
+{
+ test_gad_lat_lon_dec_enc_stability();
+ test_gad_enc_dec();
+ test_gad_to_str();
+ return 0;
+}
diff --git a/tests/gad/gad_test.ok b/tests/gad/gad_test.ok
new file mode 100644
index 00000000..ec5432a8
--- /dev/null
+++ b/tests/gad/gad_test.ok
@@ -0,0 +1,8 @@
+--- test_gad_lat_lon_dec_enc_stability
+osmo_gad_dec_lat() -> osmo_gad_enc_lat() of 16777216 values successful
+osmo_gad_dec_lon() -> osmo_gad_enc_lon() of 16777216 values successful
+--- test_gad_enc_dec
+[0] Ellipsoid-point-with-uncertainty-circle: ok
+ encoded data: 10 20 b6 0c 1d dd de 28
+--- test_gad_to_str
+[0] Ellipsoid-point-with-uncertainty-circle{lat=23.000006,lon=42.000002,unc=442.592m}