[PATCH] openbsc[master]: XID related modifications in LLC

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/.

dexter gerrit-no-reply at lists.osmocom.org
Fri Aug 5 11:28:08 UTC 2016


Hello Harald Welte,

I'd like you to reexamine a change.  Please visit

    https://gerrit.osmocom.org/652

to look at the new patch set (#6).

XID related modifications in LLC

With this commit the already existing XID mechanism has been
modified to suit the needs for the upcomming SNDCP-XID patches.

The SNDCP-XID related calls are currently disabled since the
necessary patches for gprs_sndcp.c are not yet pushed. This
commit should not break anything since it does not alter the
current behaviour (incoming XID is still just echoed, on
GMM-Reset a basic XID message is still echoed)

Change-Id: I65b9d625e72d3d61c99abdc7041773701d694d52
---
M openbsc/include/openbsc/gprs_llc.h
M openbsc/src/gprs/gprs_llc.c
M openbsc/src/gprs/v42bis.c
M openbsc/tests/sgsn/Makefile.am
4 files changed, 359 insertions(+), 74 deletions(-)


  git pull ssh://gerrit.osmocom.org:29418/openbsc refs/changes/52/652/6

diff --git a/openbsc/include/openbsc/gprs_llc.h b/openbsc/include/openbsc/gprs_llc.h
index 39d17f4..8b93784 100644
--- a/openbsc/include/openbsc/gprs_llc.h
+++ b/openbsc/include/openbsc/gprs_llc.h
@@ -4,6 +4,7 @@
 #include <stdint.h>
 #include <stdbool.h>
 #include <openbsc/gprs_sgsn.h>
+#include <openbsc/gprs_llc_xid.h>
 
 /* Section 4.7 LLC Layer Structure */
 enum gprs_llc_sapi {
@@ -148,10 +149,8 @@
 
 /* Lists holding the compression entities */
 struct comp_ent {
-	/*
-	 * In this two list_heads we will store the data and protocol
-	 * compression entities, together with their compression states 
-	 */
+	/* In this two list_heads we will store the data and protocol
+	 * compression entities, together with their compression states */
 	struct llist_head proto;
 	struct llist_head data;
 };
@@ -235,6 +234,10 @@
 int gprs_llgmm_reset_oldmsg(struct msgb* oldmsg, uint8_t sapi,
 			    struct gprs_llc_llme *llme);
 
+/* Set of LL-XID negotiation (See also: TS 101 351, Section 7.2.2.4) */
+int gprs_ll_xid_req(struct gprs_llc_lle *lle,
+		    struct gprs_llc_xid_field *l3_xid_field);
+
 /* 04.64 Chapter 7.2.1.1 LLGMM-ASSIGN */
 int gprs_llgmm_assign(struct gprs_llc_llme *llme,
 		      uint32_t old_tlli, uint32_t new_tlli);
diff --git a/openbsc/src/gprs/gprs_llc.c b/openbsc/src/gprs/gprs_llc.c
index 7724ebb..9e85f63 100644
--- a/openbsc/src/gprs/gprs_llc.c
+++ b/openbsc/src/gprs/gprs_llc.c
@@ -38,8 +38,312 @@
 #include <openbsc/gprs_llc.h>
 #include <openbsc/crc24.h>
 #include <openbsc/sgsn.h>
+#include <openbsc/gprs_llc_xid.h>
+#include <openbsc/gprs_sndcp_comp_entity.h>
+#include <openbsc/gprs_sndcp.h>
+
+
+/* FIXME: Remove this switch as soon as the XID integration in
+ * gprs_sndcp.c h is done */
+#define WITH_SNDCP_XID 1
 
 static struct gprs_llc_llme *llme_alloc(uint32_t tlli);
+static int gprs_llc_tx_xid(struct gprs_llc_lle *lle, struct msgb *msg,
+			   int command);
+static int gprs_llc_tx_u(struct msgb *msg, uint8_t sapi,
+			 int command, enum gprs_llc_u_cmd u_cmd, int pf_bit);
+
+/* BEGIN XID RELATED */
+
+/* Generate XID message */
+static int gprs_llc_generate_xid(uint8_t *bytes, int bytes_len,
+				 struct gprs_llc_xid_field *l3_xid_field,
+				 struct gprs_llc_llme *llme)
+{
+	/* Note: Called by gprs_ll_xid_req() */
+
+	LLIST_HEAD(xid_fields);
+
+	struct gprs_llc_xid_field xid_version;
+	struct gprs_llc_xid_field xid_n201u;
+	struct gprs_llc_xid_field xid_n201i;
+
+	xid_version.type = GPRS_LLC_XID_T_VERSION;
+	xid_version.data = (uint8_t *) "\x00";
+	xid_version.data_len = 1;
+
+	xid_n201u.type = GPRS_LLC_XID_T_N201_U;
+	xid_n201u.data = (uint8_t *) "\x05\xf0";
+	xid_n201u.data_len = 2;
+
+	xid_n201i.type = GPRS_LLC_XID_T_N201_I;
+	xid_n201i.data = (uint8_t *) "\x05\xf0";
+	xid_n201i.data_len = 2;
+
+	/* Add layer 3 XID field (if present) */
+	if (l3_xid_field) {
+		/* Enforce layer 3 XID type (just to be sure) */
+		l3_xid_field->type = GPRS_LLC_XID_T_L3_PAR;
+
+		/* Add Layer 3 XID field to the list */
+		llist_add(&l3_xid_field->list, &xid_fields);
+	}
+
+	/* Add locally managed XID Fields */
+	llist_add(&xid_n201i.list, &xid_fields);
+	llist_add(&xid_n201u.list, &xid_fields);
+	llist_add(&xid_version.list, &xid_fields);
+
+	gprs_llc_copy_xid(&llme->xid, &xid_fields);
+
+	return gprs_llc_compile_xid(&xid_fields, bytes, bytes_len);
+}
+
+/* Generate XID message that will cause the GMM to reset */
+static int gprs_llc_generate_xid_for_gmm_reset(uint8_t *bytes,
+					       int bytes_len, uint32_t iov_ui,
+					       struct gprs_llc_llme *llme)
+{
+	/* Called by gprs_llgmm_reset() and
+	 * gprs_llgmm_reset_oldmsg() */
+
+	LLIST_HEAD(xid_fields);
+
+	struct gprs_llc_xid_field xid_reset;
+	struct gprs_llc_xid_field xid_iovui;
+
+	/* First XID component must be RESET */
+	xid_reset.type = GPRS_LLC_XID_T_RESET;
+	xid_reset.data = NULL;
+	xid_reset.data_len = 0;
+
+	/* Add new IOV-UI */
+	xid_iovui.type = GPRS_LLC_XID_T_IOV_UI;
+	xid_iovui.data = (uint8_t *) & iov_ui;
+	xid_iovui.data_len = 4;
+
+	/* Add locally managed XID Fields */
+	llist_add(&xid_iovui.list, &xid_fields);
+	llist_add(&xid_reset.list, &xid_fields);
+
+	gprs_llc_copy_xid(&llme->xid, &xid_fields);
+
+	return gprs_llc_compile_xid(&xid_fields, bytes, bytes_len);
+}
+
+/* Process an incoming XID confirmation */
+static int gprs_llc_process_xid_conf(uint8_t *bytes, int bytes_len,
+				     struct gprs_llc_lle *lle)
+{
+	/* Note: This function handles the response of a network originated
+	 * XID-Request. There XID messages reflected by the phone are analyzed
+	 * and processed here. The caller is called by rx_llc_xid(). */
+
+	int rc;
+	LLIST_HEAD(xid_fields);
+	struct gprs_llc_xid_field *xid_field;
+	struct gprs_llc_xid_field *xid_field_request;
+	struct gprs_llc_xid_field *xid_field_request_l3 = NULL;
+
+	/* Pick layer3 XID from the XID request we have sent last */
+	llist_for_each_entry(xid_field_request, &lle->llme->xid, list) {
+		if (xid_field_request->type == GPRS_LLC_XID_T_L3_PAR)
+			xid_field_request_l3 = xid_field_request;
+	}
+
+	/* Parse and analyze XID-Response */
+	rc = gprs_llc_parse_xid(&xid_fields, bytes, bytes_len);
+	if (rc == 0) {
+		gprs_llc_dump_xid_fields(&xid_fields, LOGL_DEBUG);
+
+		llist_for_each_entry(xid_field, &xid_fields, list) {
+
+			/* Forward SNDCP-XID fields to Layer 3 (SNDCP) */
+			if (xid_field->type == GPRS_LLC_XID_T_L3_PAR) {
+#if WITH_SNDCP_XID == 1
+				sndcp_sn_xid_conf(xid_field,
+						  xid_field_request_l3,
+						  lle);
+#endif
+			}
+
+			/* Process LLC-XID fields: */
+			else {
+
+				/* FIXME: Do something more useful with the
+				 * echoed XID-Information. Currently we
+				 * just ignore the response completely and
+				 * by doing so we blindly accept any changes
+				 * the MS might have done to the our XID
+				 * inquiry. There is a remainig risk of
+				 * malfunction! */
+				LOGP(DLLC, LOGL_NOTICE,
+				     "Ignoring XID-Field: XID: type=%i, data_len=%i, data=%s\n",
+				     xid_field->type, xid_field->data_len,
+				     xid_field->data);
+
+			}
+		}
+	}
+
+	/* Flush pending XID fields */
+	gprs_llc_free_xid(&lle->llme->xid);
+
+	return 0;
+}
+
+
+/* Process an incoming XID indication and generate an appropiate response */
+static int gprs_llc_process_xid_ind(uint8_t *bytes_request,
+				    int bytes_request_len,
+				    uint8_t *bytes_response,
+				    int bytes_response_maxlen,
+				    struct gprs_llc_lle *lle)
+{
+	/* Note: This function computes the response that is sent back to the
+	 * phone when a phone originated XID is received. The function is
+	 * called by rx_llc_xid() */
+
+	int rc;
+	LLIST_HEAD(xid_fields);
+	LLIST_HEAD(xid_fields_response);
+
+	struct gprs_llc_xid_field *xid_field;
+	struct gprs_llc_xid_field *xid_field_response;
+
+	/* Flush eventually pending XID fields */
+	gprs_llc_free_xid(&lle->llme->xid);
+
+	/* Parse and analyze XID-Request */
+	rc = gprs_llc_parse_xid(&xid_fields, bytes_request,
+				bytes_request_len);
+	if (rc == 0) {
+		gprs_llc_dump_xid_fields(&xid_fields, LOGL_DEBUG);
+
+		llist_for_each_entry(xid_field, &xid_fields, list) {
+			/* Forward SNDCP-XID fields to Layer 3 (SNDCP) */
+			if (xid_field->type == GPRS_LLC_XID_T_L3_PAR) {
+#if WITH_SNDCP_XID == 1
+				xid_field_response =
+				    talloc_zero(NULL,
+						struct gprs_llc_xid_field);
+				rc = sndcp_sn_xid_ind(xid_field,
+						      xid_field_response,
+						      lle);
+				if (rc == 0)
+					llist_add(&xid_field_response->
+						  list,
+						  &xid_fields_response);
+				else
+					talloc_free(xid_field_response);
+#endif
+			}
+
+			/* Process LLC-XID fields: */
+			else {
+				/* FIXME: Check the incoming XID parameters for
+				 * for validity. Currently we just blindly
+				 * accept all XID fields by just echoing them.
+				 * There is a remaining risk of malfunction
+				 * when a phone submits values which defer from
+				 * the default! */
+				LOGP(DLLC, LOGL_NOTICE,
+				     "Echoing XID-Field: XID: type=%i, data_len=%i, data=%s\n",
+				     xid_field->type, xid_field->data_len,
+				     osmo_hexdump_nospc(xid_field->data,
+							xid_field->
+							data_len));
+				xid_field_response =
+				    gprs_llc_duplicate_xid_field
+				    (xid_field);
+				llist_add(&xid_field_response->list,
+					  &xid_fields_response);
+			}
+		}
+
+		rc = gprs_llc_compile_xid(&xid_fields_response,
+					  bytes_response,
+					  bytes_response_maxlen);
+		gprs_llc_free_xid(&xid_fields_response);
+	}
+	gprs_llc_free_xid(&xid_fields);
+
+	return rc;
+}
+
+/* Dispatch XID indications and responses comming from the Phone */
+static void rx_llc_xid(struct gprs_llc_lle *lle,
+		       struct gprs_llc_hdr_parsed *gph)
+{
+	uint8_t response[1024];
+	int response_len;
+
+	/* FIXME: 8.5.3.3: check if XID is invalid */
+	if (gph->is_cmd) {
+		LOGP(DLLC, LOGL_NOTICE,
+		     "Received XID indication from phone.\n");
+
+		struct msgb *resp;
+		uint8_t *xid;
+		resp = msgb_alloc_headroom(4096, 1024, "LLC_XID");
+
+		response_len =
+		    gprs_llc_process_xid_ind(gph->data, gph->data_len,
+					     response, sizeof(response),
+					     lle);
+		xid = msgb_put(resp, response_len);
+		memcpy(xid, response, response_len);
+
+		gprs_llc_tx_xid(lle, resp, 0);
+	} else {
+		LOGP(DLLC, LOGL_NOTICE,
+		     "Received XID confirmation from phone.\n");
+		gprs_llc_process_xid_conf(gph->data, gph->data_len, lle);
+		/* FIXME: if we had sent a XID reset, send
+		 * LLGMM-RESET.conf to GMM */
+	}
+}
+
+
+/* Set of LL-XID negotiation (See also: TS 101 351, Section 7.2.2.4) */
+int gprs_ll_xid_req(struct gprs_llc_lle *lle,
+		    struct gprs_llc_xid_field *l3_xid_field)
+{
+	/* Note: This functions is calle from gprs_sndcp.c */
+
+	uint8_t xid_bytes[1024];;
+	int xid_bytes_len;
+	uint8_t *xid;
+	struct msgb *msg;
+
+	/* Generate XID */
+	xid_bytes_len =
+	    gprs_llc_generate_xid(xid_bytes, sizeof(xid_bytes),
+				  l3_xid_field, lle->llme);
+
+
+	/* Only perform XID sending if the XID message contains something */
+	if (xid_bytes_len > 0) {
+		/* Transmit XID bytes */
+		msg = msgb_alloc_headroom(4096, 1024, "LLC_XID");
+		xid = msgb_put(msg, xid_bytes_len);
+		memcpy(xid, xid_bytes, xid_bytes_len);
+		LOGP(DLLC, LOGL_NOTICE,
+		     "Sending XID request to phone...\n");
+		gprs_llc_tx_xid(lle, msg, 1);
+	} else {
+		LOGP(DLLC, LOGL_ERROR,
+		     "XID-Message generation failed, XID not sent!\n");
+		return -EINVAL;
+	}
+
+	return 0;
+}
+
+/* END XID RELATED */
+
+
+
 
 /* Entry function from upper level (LLC), asking us to transmit a BSSGP PDU
  * to a remote MS (identified by TLLI) at a BTS identified by its BVCI and NSEI */
@@ -51,7 +355,7 @@
 	memset(&dup, 0, sizeof(dup));
 	/* before we have received some identity from the MS, we might
 	 * not yet have a MMC context (e.g. XID negotiation of primarly
-	 * LLC connection fro GMM sapi). */
+	 * LLC connection from GMM sapi). */
 	if (mmctx) {
 		dup.imsi = mmctx->imsi;
 		dup.drx_parms = mmctx->drx_parms;
@@ -246,11 +550,18 @@
 
 	llist_add(&llme->list, &gprs_llc_llmes);
 
+	INIT_LLIST_HEAD(&llme->comp.proto);
+	INIT_LLIST_HEAD(&llme->comp.data);
+	INIT_LLIST_HEAD(&llme->xid);
+
 	return llme;
 }
 
 static void llme_free(struct gprs_llc_llme *llme)
 {
+	gprs_sndcp_comp_entities_free(&llme->comp.proto);
+	gprs_sndcp_comp_entities_free(&llme->comp.data);
+	gprs_llc_free_xid(&llme->xid);
 	llist_del(&llme->list);
 	talloc_free(llme);
 }
@@ -464,54 +775,6 @@
 
 	/* Send BSSGP-DL-UNITDATA.req */
 	return _bssgp_tx_dl_ud(msg, mmctx);
-}
-
-/* According to 6.4.1.6 / Figure 11 */
-static int msgb_put_xid_par(struct msgb *msg, uint8_t type, uint8_t length, uint8_t *data)
-{
-	uint8_t header_len = 1;
-	uint8_t *cur;
-
-	/* type is a 5-bit field... */
-	if (type > 0x1f)
-		return -EINVAL;
-
-	if (length > 3)
-		header_len = 2;
-
-	cur = msgb_put(msg, length + header_len);
-
-	/* build the header without or with XL bit */
-	if (length <= 3) {
-		*cur++ = (type << 2) | (length & 3);
-	} else {
-		*cur++ = 0x80 | (type << 2) | (length >> 6);
-		*cur++ = (length << 2);
-	}
-
-	/* copy over the payload of the parameter*/
-	memcpy(cur, data, length);
-
-	return length + header_len;
-}
-
-static void rx_llc_xid(struct gprs_llc_lle *lle,
-			struct gprs_llc_hdr_parsed *gph)
-{
-	/* FIXME: 8.5.3.3: check if XID is invalid */
-	if (gph->is_cmd) {
-		/* FIXME: implement XID negotiation using SNDCP */
-		struct msgb *resp;
-		uint8_t *xid;
-		resp = msgb_alloc_headroom(4096, 1024, "LLC_XID");
-		xid = msgb_put(resp, gph->data_len);
-		memcpy(xid, gph->data, gph->data_len);
-		gprs_llc_tx_xid(lle, resp, 0);
-	} else {
-		/* FIXME: if we had sent a XID reset, send
-		 * LLGMM-RESET.conf to GMM */
-		/* FIXME: implement XID negotiation using SNDCP */
-	}
 }
 
 static int gprs_llc_hdr_rx(struct gprs_llc_hdr_parsed *gph,
@@ -784,17 +1047,24 @@
 {
 	struct msgb *msg = msgb_alloc_headroom(4096, 1024, "LLC_XID");
 	struct gprs_llc_lle *lle = &llme->lle[1];
+	uint8_t xid_bytes[1024];
+	int xid_bytes_len;
+	uint8_t *xid;
 
+	LOGP(DLLC, LOGL_NOTICE, "LLGM Reset\n");
 	if (RAND_bytes((uint8_t *) &llme->iov_ui, 4) != 1) {
 		LOGP(DLLC, LOGL_NOTICE, "RAND_bytes failed for LLC XID reset, "
 		     "falling back to rand()\n");
 		llme->iov_ui = rand();
 	}
 
-	/* First XID component must be RESET */
-	msgb_put_xid_par(msg, GPRS_LLC_XID_T_RESET, 0, NULL);
-	/* randomly select new IOV-UI */
-	msgb_put_xid_par(msg, GPRS_LLC_XID_T_IOV_UI, 4, (uint8_t *) &llme->iov_ui);
+	/* Generate XID message */
+	xid_bytes_len = gprs_llc_generate_xid_for_gmm_reset(xid_bytes,
+					sizeof(xid_bytes),llme->iov_ui,llme);
+	if(xid_bytes_len < 0)
+		return -EINVAL;
+	xid = msgb_put(msg, xid_bytes_len);
+	memcpy(xid, xid_bytes, xid_bytes_len);
 
 	/* Reset some of the LLC parameters. See GSM 04.64, 8.5.3.1 */
 	lle->vu_recv = 0;
@@ -810,17 +1080,24 @@
 			    struct gprs_llc_llme *llme)
 {
 	struct msgb *msg = msgb_alloc_headroom(4096, 1024, "LLC_XID");
+	uint8_t xid_bytes[1024];
+	int xid_bytes_len;
+	uint8_t *xid;
 
+	LOGP(DLLC, LOGL_NOTICE, "LLGM Reset\n");
 	if (RAND_bytes((uint8_t *) &llme->iov_ui, 4) != 1) {
 		LOGP(DLLC, LOGL_NOTICE, "RAND_bytes failed for LLC XID reset, "
 		     "falling back to rand()\n");
 		llme->iov_ui = rand();
 	}
 
-	/* First XID component must be RESET */
-	msgb_put_xid_par(msg, GPRS_LLC_XID_T_RESET, 0, NULL);
-	/* randomly select new IOV-UI */
-	msgb_put_xid_par(msg, GPRS_LLC_XID_T_IOV_UI, 4, (uint8_t *) &llme->iov_ui);
+	/* Generate XID message */
+	xid_bytes_len = gprs_llc_generate_xid_for_gmm_reset(xid_bytes,
+					sizeof(xid_bytes),llme->iov_ui,llme);
+	if(xid_bytes_len < 0)
+		return -EINVAL;
+	xid = msgb_put(msg, xid_bytes_len);
+	memcpy(xid, xid_bytes, xid_bytes_len);
 
 	/* FIXME: Start T200, wait for XID response */
 
diff --git a/openbsc/src/gprs/v42bis.c b/openbsc/src/gprs/v42bis.c
index a306107..65d8814 100644
--- a/openbsc/src/gprs/v42bis.c
+++ b/openbsc/src/gprs/v42bis.c
@@ -306,7 +306,7 @@
                 {
                     if (ss->transparent)
                     {
-                        printf("Going compressed\n");
+                        DEBUGP(DV42BIS,"Going compressed\n");
                         /* 7.8.1 Transition to compressed mode */
                         /* Switch out of transparent now, between codes. We need to send the octet which did not
                         match, just before switching. */
@@ -328,7 +328,7 @@
                 {
                     if (!ss->transparent)
                     {
-                        printf("Going transparent\n");
+                        DEBUGP(DV42BIS,"Going transparent\n");
                         /* 7.8.2 Transition to transparent mode */
                         /* Switch into transparent now, between codes, and the unmatched octet should
                            go out in transparent mode, just below */
@@ -397,7 +397,7 @@
     {
         if (s->compress.dict[i].parent_code != 0xFFFF)
         {
-            printf("Entry %4x, prior %4x, leaves %d, octet %2x\n", i, s->compress.dict[i].parent_code, s->compress.dict[i].leaves, s->compress.dict[i].node_octet);
+            DEBUGP(DV42BIS,"Entry %4x, prior %4x, leaves %d, octet %2x\n", i, s->compress.dict[i].parent_code, s->compress.dict[i].leaves, s->compress.dict[i].node_octet);
         }
     }
     return 0;
@@ -450,13 +450,13 @@
                 ss->escaped = FALSE;
                 if (code == V42BIS_ECM)
                 {
-                    printf("Hit V42BIS_ECM\n");
+                    DEBUGP(DV42BIS,"Hit V42BIS_ECM\n");
                     ss->transparent = FALSE;
                     code_len = ss->v42bis_parm_c2;
                 }
                 else if (code == V42BIS_EID)
                 {
-                    printf("Hit V42BIS_EID\n");
+                    DEBUGP(DV42BIS,"Hit V42BIS_EID\n");
                     ss->output_buf[ss->output_octet_count++] = ss->escape_code - 1;
                     if (ss->output_octet_count >= ss->max_len - s->v42bis_parm_n7)
                     {
@@ -466,11 +466,11 @@
                 }
                 else if (code == V42BIS_RESET)
                 {
-                    printf("Hit V42BIS_RESET\n");
+                    DEBUGP(DV42BIS,"Hit V42BIS_RESET\n");
                 }
                 else
                 {
-                    printf("Hit V42BIS_???? - %" PRIu32 "\n", code);
+                    DEBUGP(DV42BIS,"Hit V42BIS_???? - %" PRIu32 "\n", code);
                 }
             }
             else if (code == ss->escape_code)
@@ -496,17 +496,17 @@
                 switch (new_code)
                 {
                 case V42BIS_ETM:
-                    printf("Hit V42BIS_ETM\n");
+                    DEBUGP(DV42BIS,"Hit V42BIS_ETM\n");
                     ss->transparent = TRUE;
                     code_len = 8;
                     break;
                 case V42BIS_FLUSH:
-                    printf("Hit V42BIS_FLUSH\n");
+                    DEBUGP(DV42BIS,"Hit V42BIS_FLUSH\n");
                     v42bis_decompress_flush(s);
                     break;
                 case V42BIS_STEPUP:
                     /* We need to increase the codeword size */
-                    printf("Hit V42BIS_STEPUP\n");
+                    DEBUGP(DV42BIS,"Hit V42BIS_STEPUP\n");
                     if (ss->v42bis_parm_c3 >= s->v42bis_parm_n2)
                     {
                         /* Invalid condition */
@@ -543,7 +543,7 @@
             /* Trace back through the octets which form the string, and output them. */
             while (code >= V42BIS_N5)
             {
-if (code > 4095) {printf("Code is 0x%" PRIu32 "\n", code); exit(2);}
+if (code > 4095) {DEBUGP(DV42BIS,"Code is 0x%" PRIu32 "\n", code); exit(2);}
                 *string-- = ss->dict[code].node_octet;
                 code = ss->dict[code].parent_code;
             }
@@ -627,7 +627,7 @@
     {
         if (s->decompress.dict[i].parent_code != 0xFFFF)
         {
-            printf("Entry %4x, prior %4x, leaves %d, octet %2x\n", i, s->decompress.dict[i].parent_code, s->decompress.dict[i].leaves, s->decompress.dict[i].node_octet);
+            DEBUGP(DV42BIS,"Entry %4x, prior %4x, leaves %d, octet %2x\n", i, s->decompress.dict[i].parent_code, s->decompress.dict[i].leaves, s->decompress.dict[i].node_octet);
         }
     }
     return 0;
diff --git a/openbsc/tests/sgsn/Makefile.am b/openbsc/tests/sgsn/Makefile.am
index b6036c7..3b34452 100644
--- a/openbsc/tests/sgsn/Makefile.am
+++ b/openbsc/tests/sgsn/Makefile.am
@@ -30,6 +30,11 @@
 	$(top_builddir)/src/gprs/gprs_gb_parse.o \
 	$(top_builddir)/src/gprs/oap.o \
 	$(top_builddir)/src/gprs/oap_messages.o \
+        $(top_builddir)/src/gprs/gprs_llc_xid.o \
+        $(top_builddir)/src/gprs/gprs_sndcp_xid.o \
+	$(top_builddir)/src/gprs/gprs_sndcp_comp_entity.o \
+        $(top_builddir)/src/gprs/gprs_sndcp_hdrcomp.o \
+        $(top_builddir)/src/gprs/slhc.o \
 	$(top_builddir)/src/libcommon/libcommon.a \
 	$(LIBOSMOABIS_LIBS) \
 	$(LIBOSMOCORE_LIBS) \
@@ -37,5 +42,5 @@
 	$(LIBOSMOGB_LIBS) \
 	$(LIBCARES_LIBS) \
 	$(LIBCRYPTO_LIBS) \
-	-lgtp -lrt
+	-lgtp -lrt -lm
 

-- 
To view, visit https://gerrit.osmocom.org/652
To unsubscribe, visit https://gerrit.osmocom.org/settings

Gerrit-MessageType: newpatchset
Gerrit-Change-Id: I65b9d625e72d3d61c99abdc7041773701d694d52
Gerrit-PatchSet: 6
Gerrit-Project: openbsc
Gerrit-Branch: master
Gerrit-Owner: dexter <pmaier at sysmocom.de>
Gerrit-Reviewer: Harald Welte <laforge at gnumonks.org>



More information about the gerrit-log mailing list