[PATCH] Fix MO concatenation
Alexander Malysh <[email protected]>
| Newsgroups | gmane.comp.mobile.kannel.devel |
|---|---|
| Message-ID | <[email protected]> |
Hi, attached if patch that fixes issue in MO concatenation handling. Just example: - First MO with 2 parts (from:123, to:456, reference id in concat=0, udh=A) - Second MO also with 2 parts (from:123, to:456, reference id in concat=0, udh=B) Now when we receive part 1 from first MO and then part 2 from second MO we will put them together. We are not really able to differentiate First MO parts and second MO parts but we at least able to minimize possibility to wrong assemble parts when we check whether UDH (without concatenation info) is the same. Please check attached patch. Looking for feedback... Thanks, Alexander Malysh
bb_smscconn_concat.diff
(application/octet-stream, 6.2 KB)
diff --git a/gw/bb_smscconn.c b/gw/bb_smscconn.c
index 559222d..2154ca2 100644
--- a/gw/bb_smscconn.c
+++ b/gw/bb_smscconn.c
@@ -1130,7 +1130,7 @@ Octstr *smsc2_status(int status_type)
default:
sprintf(tmp3, "unknown");
}
-
+
if (status_type == BBSTATUS_XML)
octstr_format_append(tmp, "<status>%s</status>\n\t\t<received>%ld</received>"
"\n\t\t<sent>%ld</sent>\n\t\t<failed>%ld</failed>\n\t\t"
@@ -1363,6 +1363,7 @@ typedef struct ConcatMsg {
int refnum;
int total_parts;
int num_parts;
+ Octstr *udh; /* normalized UDH */
time_t trecv;
Octstr *key; /* in dict. */
int ack; /* set to the type of ack to send when deleting. */
@@ -1387,6 +1388,7 @@ static void destroy_concatMsg(void *x)
}
gw_free(msg->parts);
octstr_destroy(msg->key);
+ octstr_destroy(msg->udh);
gw_free(msg);
}
@@ -1397,7 +1399,7 @@ static void init_concat_handler(void)
incoming_concat_msgs = dict_create(max_incoming_sms_qlength > 0 ? max_incoming_sms_qlength : 1024,
destroy_concatMsg);
concat_lock = mutex_create();
- debug("bb.sms",0,"smsbox MO concatenated message handling enabled");
+ debug("bb.sms",0,"MO concatenated message handling enabled");
}
static void shutdown_concat_handler(void)
@@ -1409,7 +1411,7 @@ static void shutdown_concat_handler(void)
incoming_concat_msgs = NULL;
concat_lock = NULL;
- debug("bb.sms",0,"smsbox MO concatenated message handling cleaned up");
+ debug("bb.sms",0,"MO concatenated message handling cleaned up");
}
static void clear_old_concat_parts(void)
@@ -1505,7 +1507,7 @@ static void clear_old_concat_parts(void)
static int check_concatenation(Msg **pmsg, Octstr *smscid)
{
Msg *msg = *pmsg;
- int l, iel, refnum, pos, c, part, totalparts, i, sixteenbit;
+ int l, iel = 0, refnum, pos, c, part, totalparts, i, sixteenbit;
Octstr *udh = msg->sms.udhdata, *key;
ConcatMsg *cmsg;
int ret = concat_complete;
@@ -1516,7 +1518,7 @@ static int check_concatenation(Msg **pmsg, Octstr *smscid)
for (pos = 1, c = -1; pos < l - 1; pos += iel + 2) {
iel = octstr_get_char(udh, pos + 1);
- if ((c = octstr_get_char(udh,pos)) == 0 || c == 8)
+ if ((c = octstr_get_char(udh, pos)) == 0 || c == 8)
break;
}
if (pos >= l) /* no concat UDH found. */
@@ -1525,7 +1527,7 @@ static int check_concatenation(Msg **pmsg, Octstr *smscid)
/* c = 0 means 8 bit, c = 8 means 16 bit concat info */
sixteenbit = (c == 8);
refnum = (!sixteenbit) ? octstr_get_char(udh, pos + 2) :
- (octstr_get_char(udh, pos + 2) << 8) | octstr_get_char(udh, pos + 3);
+ (octstr_get_char(udh, pos + 2) << 8) | octstr_get_char(udh, pos + 3);
totalparts = octstr_get_char(udh, pos + 3 + sixteenbit);
part = octstr_get_char(udh, pos + 4 + sixteenbit);
@@ -1535,17 +1537,27 @@ static int check_concatenation(Msg **pmsg, Octstr *smscid)
return concat_none;
}
+ /* extract UDH */
+ udh = octstr_duplicate(msg->sms.udhdata);
+ octstr_delete(udh, pos, iel + 2);
+ if (octstr_len(udh) <= 1) /* no other UDH elements. */
+ octstr_delete(udh, 0, octstr_len(udh));
+ else
+ octstr_set_char(udh, 0, octstr_len(udh) - 1);
+
debug("bb.sms.splits", 0, "Got part %d [ref %d, total parts %d] of message from %s. Dump follows:",
- part, refnum,totalparts, octstr_get_cstr(msg->sms.sender));
+ part, refnum, totalparts, octstr_get_cstr(msg->sms.sender));
- msg_dump(msg,0);
+ msg_dump(msg, 0);
- key = octstr_format("%S %S %S %d", msg->sms.sender, msg->sms.receiver, smscid, refnum);
+ key = octstr_format("'%S' '%S' '%S' '%d' '%d' '%H'", msg->sms.sender, msg->sms.receiver, smscid, refnum, totalparts, udh);
mutex_lock(concat_lock);
if ((cmsg = dict_get(incoming_concat_msgs, key)) == NULL) {
cmsg = gw_malloc(sizeof(*cmsg));
cmsg->refnum = refnum;
cmsg->total_parts = totalparts;
+ cmsg->udh = udh;
+ udh = NULL;
cmsg->num_parts = 0;
cmsg->key = octstr_duplicate(key);
cmsg->ack = ack_success;
@@ -1555,18 +1567,7 @@ static int check_concatenation(Msg **pmsg, Octstr *smscid)
dict_put(incoming_concat_msgs, key, cmsg);
}
octstr_destroy(key);
-
- if (totalparts != cmsg->total_parts) {
- /* totalparts in udh and cmsg not equal assume bad message */
- error(0, "Totalparts in UDH doesn't match received before, "
- "total parts <%d>:<%d> part %d, ref %d, from %s, to %s. Discarded!",
- cmsg->total_parts, totalparts, part, refnum, octstr_get_cstr(msg->sms.sender), octstr_get_cstr(msg->sms.receiver));
- mutex_unlock(concat_lock);
- store_save_ack(msg, ack_success);
- msg_destroy(msg);
- *pmsg = msg = NULL;
- return concat_error;
- }
+ octstr_destroy(udh);
/* check if we have seen message part before... */
if (cmsg->parts[part - 1] != NULL) {
@@ -1607,26 +1608,16 @@ static int check_concatenation(Msg **pmsg, Octstr *smscid)
} else
*pmsg = msg; /* return the message part. */
+ /* fix up UDH */
+ octstr_destroy(msg->sms.udhdata);
+ msg->sms.udhdata = cmsg->udh;
+ cmsg->udh = NULL;
+
/* Delete it from the queue and from the Dict. */
/* Note: dict_put with NULL value delete and destroy value */
dict_put(incoming_concat_msgs, cmsg->key, NULL);
mutex_unlock(concat_lock);
- /* fix up UDH */
- udh = msg->sms.udhdata;
- l = octstr_len(udh);
- for (pos = 1; pos < l - 1; pos += iel + 2) {
- iel = octstr_get_char(udh, pos + 1);
- if ((c = octstr_get_char(udh, pos)) == 0 || c == 8) {
- octstr_delete(udh, pos, iel + 2);
-
- if (octstr_len(udh) <= 1) /* no other UDH elements. */
- octstr_delete(udh, 0, octstr_len(udh));
- else
- octstr_set_char(udh, 0, octstr_len(udh) - 1);
- break;
- }
- }
debug("bb.sms.splits", 0, "Got full message [ref %d] of message from %s to %s. Dumping: ",
refnum, octstr_get_cstr(msg->sms.sender), octstr_get_cstr(msg->sms.receiver));
msg_dump(msg,0);