4 * Copyright (c) 2012-2013 Samsung Electronics Co., Ltd.
6 * Licensed under the Apache License, Version 2.0 (the "License");
7 * you may not use this file except in compliance with the License.
8 * You may obtain a copy of the License at
10 * http://www.apache.org/licenses/LICENSE-2.0
12 * Unless required by applicable law or agreed to in writing, software
13 * distributed under the License is distributed on an "AS IS" BASIS,
14 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15 * See the License for the specific language governing permissions and
16 * limitations under the License.
24 #include <ITapiNetText.h>
26 #include <map_bmessage.h>
27 #include <bluetooth_map_agent.h>
30 #define BT_SMS_DATA_MAX_LEN 165
32 #define BMSG_TAG "BEGIN:BMSG\r\n"
33 #define VER_TAG "VERSION:"
34 #define STATUS_TAG "STATUS:"
35 #define TYPE_TAG "TYPE:"
36 #define FOLDER_TAG "FOLDER:"
37 #define VCARD_BEGIN_TAG "BEGIN:VCARD\r\n"
38 #define VCARD_END_TAG "END:VCARD\r\n"
39 #define VCARD_N_TAG "N:"
40 #define VCARD_FN_TAG "FN:"
41 #define VCARD_TEL_TAG "TEL:"
42 #define VCARD_EMAIL_TAG "EMAIL:"
43 #define BENV_TAG "BEGIN:BENV\r\n"
44 #define BBODY_TAG "BEGIN:BBODY\r\n"
45 #define MSG_TAG "BEGIN:MSG\r\n"
46 #define PARTID_TAG "PARTID:"
47 #define ENCODING_TAG "ENCODING:"
48 #define CHARSET_TAG "CHARSET:"
49 #define LANGUAGE_TAG "LANGUAGE:"
50 #define LENGTH_TAG "LENGTH:"
53 void print_bmsg(struct bmsg_data *bmsg)
58 struct benv_data *env_data = NULL;
60 DBG("bmsg->version = %s", bmsg->version);
61 DBG("bmsg->status = %s", bmsg->status);
62 DBG("bmsg->type = %s", bmsg->type);
63 DBG("bmsg->folder = %s", bmsg->folder);
64 DBG("bmsg->originator_vcard_data->version = %s",
65 bmsg->originator_vcard_data->version);
66 DBG("bmsg->originator_vcard_data->n = %s",
67 bmsg->originator_vcard_data->n);
70 env_data = g_slist_nth_data(bmsg->envelope_data->env_data, i);
71 while (env_data != NULL) {
73 DBG("env_data = %d", env_data->encapsulation_level);
75 struct bmsg_vcard *rvcard;
77 rvcard = g_slist_nth_data(env_data->recipient_vcard, k);
79 while (rvcard != NULL) {
82 if (rvcard->version != NULL)
83 DBG("vcard->version = %s\n", rvcard->version);
84 if (rvcard->n != NULL)
85 DBG("vcard->n = %s\n", rvcard->n);
86 if (rvcard->fn != NULL)
87 DBG("vcard->fn = %s\n", rvcard->fn);
88 if (rvcard->tel != NULL)
89 DBG("vcard->tel = %s\n", rvcard->tel);
90 if (rvcard->email != NULL)
91 DBG("vcard->email = %s\n", rvcard->email);
93 rvcard = g_slist_nth_data(env_data->recipient_vcard, k);
96 if (env_data->body_content != NULL) {
97 DBG("env_data->body_content->length = %"
98 G_GUINT64_FORMAT "\n",
99 env_data->body_content->length);
100 DBG("env_data->body_content->msg = %s\n",
101 env_data->body_content->msg);
109 env_data = g_slist_nth_data(bmsg->envelope_data->env_data, i);
113 static gchar *__bt_unpack_gsm7bit_msg(const char* pdu, int in_len)
118 gchar data[BT_SMS_DATA_MAX_LEN + 1] = {0,};
120 for (i = 0; i < in_len; i++) {
122 data[i] = pdu[pos] & 0x7F;
127 data[i] = (pdu[pos - 1] >> shift) |
128 (pdu[pos] << (8 - shift));
137 DBG("msg = %s\n", data);
138 return g_strdup(data);
141 static gchar *__bt_get_msg_body_from_pdu(gchar *pdu, guint64 pdu_len)
149 int phone_num_len = 0;
151 char msg_data[BT_SMS_DATA_MAX_LEN + 1] = {0,};
152 unsigned char pdu_data[TAPI_NETTEXT_MSG_SIZE_MAX] = {0,};
154 for (i = 0; i < (pdu_len - 1);) {
155 snprintf(temp, sizeof(temp), "%c%c", pdu[i], pdu[i+1]);
157 pdu_data[j] = g_ascii_strtoull(temp, NULL, 16);
158 DBG("pdu_data = %02x\n", pdu_data[j]);
163 DBG("pdu[%d] = %x\n", index, pdu_data[index]);
164 if (pdu[index] == 0x00)
167 index = index + pdu_data[index];
172 if (pdu_data[index] & 0x40)
175 DBG("udh = %d", udh);
180 /* phone number length */
182 DBG("pdu[%d] = %x\n", index, pdu_data[index]);
184 if ((pdu_data[index] % 2) == 0)
185 phone_num_len = pdu_data[index] / 2;
187 phone_num_len = pdu_data[index] / 2 + 1;
189 DBG("phone_num_len [%d]\n", phone_num_len);
191 /* phone number type */
194 /* phone_num_len/2 encoded phone num length */
195 index = index + phone_num_len;
203 dcs = pdu_data[index];
204 coding_scheme = (dcs & 0x0C) >> 2;
205 DBG("coding_scheme = %d\n", coding_scheme);
212 int udl = pdu_data[index];
213 DBG("udl = %x\n", udl);
218 memcpy(msg_data, (void*)&pdu_data[index], udl);
220 return __bt_unpack_gsm7bit_msg(msg_data, udl);
223 char *bmsg_get_msg_folder(struct bmsg_data *bmsg)
225 return g_strdup(bmsg->folder);
228 char *bmsg_get_msg_body(struct bmsg_data *bmsg, gboolean utf)
230 struct benv_data *env_data;
233 env_data = g_slist_nth_data(bmsg->envelope_data->env_data, i);
235 while (env_data != NULL) {
236 if (env_data->body_content != NULL) {
237 DBG("env_data->body_content->msg = %s\n",
238 env_data->body_content->msg);
239 DBG("env_data->body_content->length = %"
240 G_GUINT64_FORMAT "\n",
241 env_data->body_content->length);
244 return __bt_get_msg_body_from_pdu(
245 env_data->body_content->msg,
246 env_data->body_content->length);
249 env_data->body_content->msg,
250 env_data->body_content->length);
258 env_data = g_slist_nth_data(bmsg->envelope_data->env_data, i);
264 GSList *bmsg_get_msg_recepients(struct bmsg_data *bmsg)
266 struct benv_data *env_data;
267 GSList *receiver = NULL;
270 env_data = g_slist_nth_data(bmsg->envelope_data->env_data, i);
272 while (env_data != NULL) {
274 DBG("env_data = %d", env_data->encapsulation_level);
276 struct bmsg_vcard *rvcard;
278 rvcard = g_slist_nth_data(env_data->recipient_vcard, k);
279 while (rvcard != NULL) {
282 if (rvcard->tel != NULL) {
283 DBG("vcard->tel = %s\n", rvcard->tel);
284 receiver = g_slist_append(receiver,
288 rvcard = g_slist_nth_data(env_data->recipient_vcard, k);
295 env_data = g_slist_nth_data(bmsg->envelope_data->env_data, i);
301 void bmsg_free_vcard_data(struct bmsg_vcard *vcard_data)
303 if (vcard_data == NULL)
306 g_free(vcard_data->version);
307 g_free(vcard_data->n);
308 g_free(vcard_data->fn);
309 g_free(vcard_data->tel);
310 g_free(vcard_data->email);
316 void bmsg_free_bmsg(struct bmsg_data *bmsg)
318 struct benv_data *env_data;
324 g_free(bmsg->version);
325 g_free(bmsg->status);
327 g_free(bmsg->folder);
328 bmsg_free_vcard_data(bmsg->originator_vcard_data);
330 if (bmsg->envelope_data == NULL)
333 if (bmsg->envelope_data->env_data == NULL)
336 env_data = g_slist_nth_data(bmsg->envelope_data->env_data, i);
337 while (env_data != NULL) {
339 DBG("env_data = %d", env_data->encapsulation_level);
341 struct bmsg_vcard *rvcard;
343 rvcard = g_slist_nth_data(env_data->recipient_vcard, k);
345 while (rvcard != NULL) {
347 bmsg_free_vcard_data(rvcard);
348 rvcard = g_slist_nth_data(env_data->recipient_vcard, k);
351 if (env_data->body_content != NULL) {
352 g_free(env_data->body_content->encoding);
353 g_free(env_data->body_content->charset);
354 g_free(env_data->body_content->language);
355 g_free(env_data->body_content->msg);
356 g_free(env_data->body_content);
362 env_data = g_slist_nth_data(bmsg->envelope_data->env_data, i);
369 gchar *bmsg_get_parse_sub_block(char **sub_block_data, char *element)
375 gchar *sub_block = NULL;
381 start = g_strdup_printf("BEGIN:%s\r\n", element);
382 end = g_strdup_printf("END:%s\r\n", element);
383 offset = strlen(start);
385 block_start = g_strstr_len(*sub_block_data, offset, start);
386 if (block_start == NULL)
389 if (!g_strcmp0(start, VCARD_BEGIN_TAG))
390 block_end = g_strstr_len(*sub_block_data, -1, end);
392 block_end = g_strrstr(*sub_block_data, end);
394 if (block_end == NULL)
397 len = block_end - block_start - offset;
398 sub_block = g_strndup(block_start + offset, len);
399 *sub_block_data = *sub_block_data + strlen(sub_block) + strlen(start) +
407 gchar *bmsg_get_tag_data(char **block_data, char *element)
418 if (*block_data == NULL || element == NULL)
421 block_start = g_strstr_len(*block_data, -1, element);
422 if (block_start == NULL)
425 offset = strlen(element);
427 block_end = g_strstr_len(block_start+offset, -1, end);
428 if (block_end == NULL)
431 len = block_end - block_start - offset;
432 sub_block = g_strndup(block_start + offset, len);
433 *block_data = *block_data + offset + len + CRLF_LEN;
438 struct bmsg_bbody *bmsg_get_bbody_data(gchar *block_data)
440 gchar *bbody_block_data_start;
442 struct bmsg_bbody *bbody;
445 bbody_block_data_start = block_data;
447 bbody = g_new0(struct bmsg_bbody, 1);
449 temp = bmsg_get_tag_data(&block_data, PARTID_TAG);
451 bbody->part_id = (guint16)g_ascii_strtoull(temp, NULL, 10);
455 bbody->encoding = bmsg_get_tag_data(&block_data, ENCODING_TAG);
456 bbody->charset = bmsg_get_tag_data(&block_data, CHARSET_TAG);
457 bbody->language = bmsg_get_tag_data(&block_data, LANGUAGE_TAG);
459 temp = bmsg_get_tag_data(&block_data, LENGTH_TAG);
462 bbody->length = g_ascii_strtoull(temp, NULL, 10);
466 bbody->msg = bmsg_get_parse_sub_block(&block_data, "MSG");
468 g_free(bbody_block_data_start);
473 struct bmsg_vcard *bmsg_get_vcard_data(gchar *sub_block_data)
475 gchar *vcard_block_data_start;
476 struct bmsg_vcard *vcard;
479 vcard_block_data_start = sub_block_data;
481 vcard = g_new0(struct bmsg_vcard, 1);
483 vcard->version = bmsg_get_tag_data(&sub_block_data, VER_TAG);
484 vcard->n = bmsg_get_tag_data(&sub_block_data, VCARD_N_TAG);
485 vcard->fn = bmsg_get_tag_data(&sub_block_data, VCARD_FN_TAG);
486 vcard->tel = bmsg_get_tag_data(&sub_block_data, VCARD_TEL_TAG);
487 vcard->email = bmsg_get_tag_data(&sub_block_data, VCARD_EMAIL_TAG);
489 g_free(vcard_block_data_start);
494 struct benv_data *bmsg_get_env_encapsulation_data(gchar **sub_block_data)
497 gchar *bbody_data = NULL;
498 static guint8 lvl = 1;
500 is_valid = g_strstr_len(*sub_block_data, strlen(VCARD_BEGIN_TAG),
502 if (is_valid == NULL)
508 struct benv_data *rec_data = g_new0(struct benv_data, 1);
510 rec_data->encapsulation_level = lvl;
513 while (is_valid != NULL) {
514 gchar *vcard_data = NULL;
515 struct bmsg_vcard *vcard;
517 vcard_data = bmsg_get_parse_sub_block(sub_block_data, "VCARD");
518 if (vcard_data == NULL) {
519 DBG("parse error\n");
523 vcard = bmsg_get_vcard_data(vcard_data);
525 rec_data->recipient_vcard = g_slist_append(
526 rec_data->recipient_vcard,
529 is_valid = g_strstr_len(*sub_block_data,
530 strlen(VCARD_BEGIN_TAG),
534 is_valid = g_strstr_len(*sub_block_data, strlen(BBODY_TAG), BBODY_TAG);
539 bbody_data = bmsg_get_parse_sub_block(sub_block_data, "BBODY");
540 if (bbody_data == NULL) {
541 DBG("parse error\n");
545 rec_data->body_content = bmsg_get_bbody_data(bbody_data);
550 struct bmsg_envelope *bmsg_get_envelope_data(gchar **block_data)
552 gchar *env_block_data_start;
553 gchar *sub_block_data;
554 struct bmsg_envelope *envelope_data;
555 struct benv_data *rec_data;
557 env_block_data_start = *block_data;
559 envelope_data = g_new0(struct bmsg_envelope, 1);
561 sub_block_data = bmsg_get_parse_sub_block(block_data, "BENV");
563 while (sub_block_data) {
565 rec_data = bmsg_get_env_encapsulation_data(&sub_block_data);
568 envelope_data->env_data = g_slist_append(
569 envelope_data->env_data,
572 rec_data = bmsg_get_env_encapsulation_data(
575 sub_block_data = bmsg_get_parse_sub_block(&sub_block_data,
578 g_free(sub_block_data);
580 return envelope_data;
583 struct bmsg_data *bmsg_parse(gchar *buf)
586 gchar *sub_block_data;
587 gchar *block_data_start;
588 struct bmsg_data *bmsg;
592 block_data = bmsg_get_parse_sub_block(&buf, "BMSG");
593 if (block_data == NULL)
596 block_data_start = block_data;
598 bmsg = g_new0(struct bmsg_data, 1);
600 bmsg->version = bmsg_get_tag_data(&block_data, VER_TAG);
601 if (bmsg->version == NULL)
604 bmsg->status = bmsg_get_tag_data(&block_data, STATUS_TAG);
605 if (bmsg->status == NULL)
608 bmsg->type = bmsg_get_tag_data(&block_data, TYPE_TAG);
609 if (bmsg->type == NULL)
612 bmsg->folder = bmsg_get_tag_data(&block_data, FOLDER_TAG);
613 if (bmsg->folder == NULL)
616 sub_block_data = bmsg_get_parse_sub_block(&block_data, "VCARD");
617 if (sub_block_data == NULL)
620 bmsg->originator_vcard_data = bmsg_get_vcard_data(sub_block_data);
621 if (bmsg->originator_vcard_data == NULL)
624 bmsg->envelope_data = bmsg_get_envelope_data(&block_data);
625 if (bmsg->envelope_data == NULL)
628 g_free(block_data_start);
637 bmsg_free_bmsg(bmsg);