aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--include/openbsc/gsm_04_08.h22
-rw-r--r--src/chan_alloc.c7
-rw-r--r--src/gsm_04_08.c20
3 files changed, 48 insertions, 1 deletions
diff --git a/include/openbsc/gsm_04_08.h b/include/openbsc/gsm_04_08.h
index e781677c3..cc93ff9b4 100644
--- a/include/openbsc/gsm_04_08.h
+++ b/include/openbsc/gsm_04_08.h
@@ -375,6 +375,27 @@ enum gsm48_cause_loc {
GSM48_CAUSE_LOC_NET_BEYOND = 0x0a,
};
+/* Section 10.5.2.31 RR Cause / Table 10.5.70 */
+enum gsm48_rr_cause {
+ GSM48_RR_CAUSE_NORMAL = 0x00,
+ GSM48_RR_CAUSE_ABNORMAL_UNSPEC = 0x01,
+ GSM48_RR_CAUSE_ABNORMAL_UNACCT = 0x02,
+ GSM48_RR_CAUSE_ABNORMAL_TIMER = 0x03,
+ GSM48_RR_CAUSE_ABNORMAL_NOACT = 0x04,
+ GSM48_RR_CAUSE_PREMPTIVE_REL = 0x05,
+ GSM48_RR_CAUSE_HNDOVER_IMP = 0x06,
+ GSM48_RR_CAUSE_CHAN_MODE_UNACCT = 0x07,
+ GSM48_RR_CAUSE_FREQ_NOT_IMPL = 0x08,
+ GSM48_RR_CAUSE_CALL_ClEARED = 0x41,
+ GSM48_RR_CAUSE_SEMANT_INCORR = 0x5f,
+ GSM48_RR_CAUSE_INVALID_MAND_INF = 0x60,
+ GSM48_RR_CAUSE_MSG_TYPE_N = 0x61,
+ GSM48_RR_CAUSE_MSG_TYPE_N_COMPAT= 0x62,
+ GSM48_RR_CAUSE_COND_IE_ERROR = 0x64,
+ GSM48_RR_CAUSE_NO_CELL_ALLOC_A = 0x65,
+ GSM48_RR_CAUSE_PROT_ERROR_UNSPC = 0x6f,
+};
+
/* Annex G, GSM specific cause values for mobility management */
enum gsm48_reject_value {
GSM48_REJECT_IMSI_UNKNOWN_IN_HLR = 2,
@@ -429,5 +450,6 @@ struct msgb *gsm48_msgb_alloc(void);
int gsm48_sendmsg(struct msgb *msg);
int generate_mid_from_tmsi(u_int8_t *buf, u_int32_t tmsi);
+int gsm48_send_rr_release(struct gsm_lchan *lchan);
#endif
diff --git a/src/chan_alloc.c b/src/chan_alloc.c
index 4658f12ec..7edde6e1f 100644
--- a/src/chan_alloc.c
+++ b/src/chan_alloc.c
@@ -1,7 +1,7 @@
/* GSM Channel allocation routines
*
* (C) 2008 by Harald Welte <laforge@gnumonks.org>
- * (C) 2008 by Holger Hans Peter Freyther <zecke@selfish.org>
+ * (C) 2008, 2009 by Holger Hans Peter Freyther <zecke@selfish.org>
*
* All Rights Reserved
*
@@ -212,6 +212,11 @@ int lchan_auto_release(struct gsm_lchan *lchan)
return 0;
}
+ /* Assume we have GSM04.08 running and send a release */
+ if (lchan->subscr) {
+ gsm48_send_rr_release(lchan);
+ }
+
/* spoofed? message */
if (lchan->use_count < 0) {
DEBUGP(DRLL, "Channel count is negative: %d\n", lchan->use_count);
diff --git a/src/gsm_04_08.c b/src/gsm_04_08.c
index 2739b0b0f..541ff4202 100644
--- a/src/gsm_04_08.c
+++ b/src/gsm_04_08.c
@@ -710,6 +710,26 @@ static int gsm0408_rcv_rr(struct msgb *msg)
return rc;
}
+/* 7.1.7 and 9.1.7 Channel release*/
+int gsm48_send_rr_release(struct gsm_lchan *lchan)
+{
+ struct msgb *msg = gsm48_msgb_alloc();
+ struct gsm48_hdr *gh = (struct gsm48_hdr *) msgb_put(msg, sizeof(*gh));
+ u_int8_t *cause;
+
+ msg->lchan = lchan;
+ gh->proto_discr = GSM48_PDISC_RR;
+ gh->msg_type = GSM48_MT_RR_CHAN_REL;
+
+ cause = msgb_put(msg, 1);
+ cause[0] = GSM48_RR_CAUSE_NORMAL;
+
+ DEBUGP(DRR, "Sending Channel Release: Chan: Number: %d Type: %d\n",
+ lchan->nr, lchan->type);
+
+ return gsm48_sendmsg(msg);
+}
+
/* Call Control */
static int gsm48_cc_tx_status(struct gsm_lchan *lchan)