4 * Copyright (c) 2012 Samsung Electronics Co., Ltd. All rights reserved.
6 * Contact: Madhavi Akella <madhavi.a@samsung.com>
8 * Licensed under the Apache License, Version 2.0 (the "License");
9 * you may not use this file except in compliance with the License.
10 * You may obtain a copy of the License at
12 * http://www.apache.org/licenses/LICENSE-2.0
14 * Unless required by applicable law or agreed to in writing, software
15 * distributed under the License is distributed on an "AS IS" BASIS,
16 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
17 * See the License for the specific language governing permissions and
18 * limitations under the License.
30 #include <core_object.h>
35 #include <user_request.h>
41 #include "common/TelErr.h"
45 /*=============================================================
47 ==============================================================*/
48 #define MAX_GSM_SMS_TPDU_SIZE 244
49 #define MAX_GSM_SMS_MSG_NUM 255
50 #define MAX_GSM_SMS_SERVICE_CENTER_ADDR 12 /* Maximum number of bytes of service center address */
51 #define MAX_GSM_SMS_CBMI_LIST_SIZE 100 /* Maximum number of CBMI list size for CBS 30*2=60 */
52 #define MAX_GSM_SMS_PARAM_RECORD_SIZE 156 /* Maximum number of bytes SMSP Record size (Y + 28), y : 0 ~ 128 */
53 #define MAX_GSM_SMS_STATUS_FILE_SIZE 2 /* Last Used TP-MR + SMS "Memory Cap. Exceeded" Noti Flag */
54 #define TAPI_SIM_SMSP_ADDRESS_LEN 20
56 /*=============================================================
58 ==============================================================*/
59 #define AT_SMS_DEVICE_READY 12 /* AT device ready */
60 #define SMS_DEVICE_READY 1 /* Telephony device ready */
61 #define SMS_DEVICE_NOT_READY 0 /* Telephony device not ready */
63 /*=============================================================
65 ==============================================================*/
66 #define SMS_CBMI_SELECTED_SOME 0x02 /* Some CBMIs are selected */
67 #define SMS_CBMI_SELECTED_ALL 0x01 /* All CBMIs are selected */
69 /*=============================================================
71 ==============================================================*/
72 #define AT_REC_UNREAD 0 /* Received and Unread */
73 #define AT_REC_READ 1 /* Received and Read */
74 #define AT_STO_UNSENT 2 /* Unsent */
75 #define AT_STO_SENT 3 /* Sent */
76 #define AT_ALL 4 /* Unknown */
78 /*=============================================================
80 ==============================================================*/
81 #define AT_MEMORY_AVAILABLE 0 /* Memory Available */
82 #define AT_MEMORY_FULL 1 /* Memory Full */
84 /*=============================================================
85 SIM CRSM SW1 and Sw2 Error definitions */
87 #define AT_SW1_SUCCESS 0x90
88 #define AT_SW2_SUCCESS 0
89 #define AT_SW1_LEN_RESP 0x9F
91 #define AT_MAX_RECORD_LEN 256
92 #define AT_EF_SMS_RECORD_LEN 176
94 /*=============================================================*/
97 /*=========================================================
99 ==============================================================*/
100 #define MAX_SEC_PIN_LEN 8
101 #define MAX_SEC_PUK_LEN 8
102 #define MAX_SEC_PHONE_LOCK_PW_LEN 39 /* Maximum Phone Locking Password Length */
103 #define MAX_SEC_SIM_DATA_STRING 256 /* Maximum Length of the DATA or RESPONSE. Restricted SIM Access, Generic SIM Access Message */
104 #define MAX_SEC_NUM_LOCK_TYPE 8 /* Maximum number of Lock Type used in Lock Information Message */
105 #define MAX_SEC_IMS_AUTH_LEN 512 /* Maximum Length of IMS Authentication Message */
107 /*=============================================================
109 ==============================================================*/
110 #define CR '\r' /* Carriage Return */
112 /*=============================================================
114 ==============================================================*/
115 #define SMS_SWAPBYTES16(x) (((x) & 0xffff0000) | (((x) & 0x0000ff00) >> 8) | (((x) & 0x000000ff) << 8))
117 void print_glib_list_elem(gpointer data, gpointer user_data);
119 static void on_response_class2_read_msg(TcorePending *pending, int data_len, const void *data, void *user_data);
122 gboolean util_byte_to_hex(const char *byte_pdu, char *hex_pdu, int num_bytes);
124 /* gaurav.kalra: For test */
125 void print_glib_list_elem(gpointer data, gpointer user_data)
127 char *item = (char *)data;
128 dbg("item: [%s]", item);
131 /*=============================================================
133 ==============================================================*/
134 static void on_confirmation_sms_message_send(TcorePending *p, gboolean result, void *user_data)
136 dbg("Entered Function. Request message out from queue");
138 dbg("TcorePending: [%p]", p);
139 dbg("result: [%02x]", result);
140 dbg("user_data: [%p]", user_data);
151 dbg("Exiting Function. Nothing to return");
154 /*=============================================================
156 ==============================================================*/
157 static void util_sms_free_memory(void *sms_ptr)
163 dbg("Freeing memory location: [%p]", sms_ptr);
169 err("Invalid memory location. Nothing to do.");
176 static int util_sms_decode_smsParameters(unsigned char *incoming, unsigned int length, struct telephony_sms_Params *params)
178 int alpha_id_len = 0;
182 dbg(" RecordLen = %d", length);
184 if(incoming == NULL || params == NULL)
187 alpha_id_len = length -SMS_SMSP_PARAMS_MAX_LEN;
189 if (alpha_id_len > 0)
191 if(alpha_id_len > SMS_SMSP_ALPHA_ID_LEN_MAX)
193 alpha_id_len = SMS_SMSP_ALPHA_ID_LEN_MAX;
196 for(i=0 ; i < alpha_id_len ; i++)
198 if(0xff == incoming[i])
205 memcpy(params->szAlphaId, incoming, i);
207 params->alphaIdLen = i;
209 dbg(" Alpha id length = %d", i);
214 params->alphaIdLen = 0;
215 dbg(" Alpha id length is zero");
218 //dongil01.park - start parse from here.
219 params->paramIndicator = incoming[alpha_id_len];
221 dbg(" Param Indicator = %02x", params->paramIndicator);
223 //dongil01.park(2008/12/26) - DestAddr
224 if((params->paramIndicator & SMSPValidDestAddr) == 0)
226 nOffset = nDestAddrOffset;
228 if(0x00 == incoming[alpha_id_len + nOffset] || 0xff == incoming[alpha_id_len + nOffset])
230 params->tpDestAddr.dialNumLen = 0;
232 dbg("DestAddr Length is 0");
236 if (0 < (int)incoming[alpha_id_len + nOffset])
238 params->tpDestAddr.dialNumLen = (int)(incoming[alpha_id_len + nOffset] - 1);
240 if(params->tpDestAddr.dialNumLen > SMS_SMSP_ADDRESS_LEN)
241 params->tpDestAddr.dialNumLen = SMS_SMSP_ADDRESS_LEN;
245 params->tpDestAddr.dialNumLen = 0;
248 params->tpDestAddr.numPlanId= incoming[alpha_id_len + (++nOffset)] & 0x0f ;
249 params->tpDestAddr.typeOfNum= (incoming[alpha_id_len + nOffset] & 0x70)>>4 ;
251 memcpy(params->tpDestAddr.diallingNum, &incoming[alpha_id_len + (++nOffset)], (params->tpDestAddr.dialNumLen)) ;
253 dbg("Dest TON is %d",params->tpDestAddr.typeOfNum);
254 dbg("Dest NPI is %d",params->tpDestAddr.numPlanId);
255 dbg("Dest Length = %d",params->tpDestAddr.dialNumLen);
256 dbg("Dest Addr = %s",params->tpDestAddr.diallingNum);
261 //dongil01.park(2008/12/26) - SvcAddr
262 if((params->paramIndicator & SMSPValidSvcAddr) == 0)
264 nOffset = nSCAAddrOffset;
266 if(0x00 == (int)incoming[alpha_id_len + nOffset] || 0xff == (int)incoming[alpha_id_len + nOffset])
268 params->tpSvcCntrAddr.dialNumLen = 0;
270 dbg(" SCAddr Length is 0");
274 if (0 < (int)incoming[alpha_id_len + nOffset] )
276 params->tpSvcCntrAddr.dialNumLen = (int)(incoming[alpha_id_len + nOffset] - 1);
278 if(params->tpSvcCntrAddr.dialNumLen > SMS_SMSP_ADDRESS_LEN)
279 params->tpSvcCntrAddr.dialNumLen = SMS_SMSP_ADDRESS_LEN;
281 params->tpSvcCntrAddr.numPlanId= incoming[alpha_id_len + (++nOffset)] & 0x0f ;
282 params->tpSvcCntrAddr.typeOfNum= (incoming[alpha_id_len + nOffset] & 0x70) >>4 ;
284 memcpy(params->tpSvcCntrAddr.diallingNum, &incoming[alpha_id_len + (++nOffset)], (params->tpSvcCntrAddr.dialNumLen));
286 dbg("SCAddr Length = %d ",params->tpSvcCntrAddr.dialNumLen);
287 dbg("SCAddr TON is %d",params->tpSvcCntrAddr.typeOfNum);
288 dbg("SCAddr NPI is %d",params->tpSvcCntrAddr.numPlanId);
290 for(i = 0 ; i < (int)params->tpSvcCntrAddr.dialNumLen ; i ++)
291 dbg("SCAddr = %d [%02x]",i,params->tpSvcCntrAddr.diallingNum[i]);
295 params->tpSvcCntrAddr.dialNumLen = 0;
299 else if ((0x00 < (int)incoming[alpha_id_len +nSCAAddrOffset] && (int)incoming[alpha_id_len +nSCAAddrOffset] <= 12)
300 || 0xff != (int)incoming[alpha_id_len +nSCAAddrOffset])
302 nOffset = nSCAAddrOffset;
304 if(0x00 == (int)incoming[alpha_id_len + nOffset] || 0xff == (int)incoming[alpha_id_len + nOffset])
306 params->tpSvcCntrAddr.dialNumLen = 0;
307 dbg("SCAddr Length is 0");
312 if (0 < (int)incoming[alpha_id_len + nOffset] )
314 params->tpSvcCntrAddr.dialNumLen = (int)(incoming[alpha_id_len + nOffset] - 1);
316 params->tpSvcCntrAddr.dialNumLen = incoming[alpha_id_len + nOffset] -1;
318 if(params->tpSvcCntrAddr.dialNumLen > SMS_SMSP_ADDRESS_LEN)
319 params->tpSvcCntrAddr.dialNumLen = SMS_SMSP_ADDRESS_LEN;
321 params->tpSvcCntrAddr.numPlanId= incoming[alpha_id_len + (++nOffset)] & 0x0f ;
322 params->tpSvcCntrAddr.typeOfNum= (incoming[alpha_id_len + nOffset] & 0x70) >>4 ;
324 memcpy(params->tpSvcCntrAddr.diallingNum, &incoming[alpha_id_len + (++nOffset)],
325 (params->tpSvcCntrAddr.dialNumLen)) ;
327 dbg("SCAddr Length = %d ",params->tpSvcCntrAddr.dialNumLen);
328 dbg("SCAddr TON is %d",params->tpSvcCntrAddr.typeOfNum);
329 dbg("SCAddr NPI is %d",params->tpSvcCntrAddr.numPlanId);
331 for(i = 0 ; i < (int)params->tpSvcCntrAddr.dialNumLen ; i ++)
332 dbg("SCAddr = %d [%02x]",i,params->tpSvcCntrAddr.diallingNum[i]);
336 params->tpSvcCntrAddr.dialNumLen = 0;
342 if((params->paramIndicator & SMSPValidPID) == 0 && (alpha_id_len + nPIDOffset) < MAX_GSM_SMS_PARAM_RECORD_SIZE)
344 params->tpProtocolId = incoming[alpha_id_len + nPIDOffset];
346 if((params->paramIndicator & SMSPValidDCS) == 0 && (alpha_id_len + nDCSOffset) < MAX_GSM_SMS_PARAM_RECORD_SIZE)
348 params->tpDataCodingScheme = incoming[alpha_id_len + nDCSOffset];
350 if((params->paramIndicator & SMSPValidVP) == 0 && (alpha_id_len + nVPOffset) < MAX_GSM_SMS_PARAM_RECORD_SIZE)
352 params->tpValidityPeriod = incoming[alpha_id_len + nVPOffset];
355 dbg(" Alpha Id(Len) = %d",(int)params->alphaIdLen);
357 for (i=0; i< (int)params->alphaIdLen ; i++)
359 dbg(" Alpha Id = [%d] [%c]",i,params->szAlphaId[i]);
361 dbg(" PID = %d",params->tpProtocolId);
362 dbg(" DCS = %d",params->tpDataCodingScheme);
363 dbg(" VP = %d",params->tpValidityPeriod);
369 /*=============================================================
371 ==============================================================*/
372 static gboolean on_event_sms_ready_status(CoreObject *o, const void *event_info, void *user_data)
374 struct tnoti_sms_ready_status readyStatusInfo = {0,};
376 GSList* tokens = NULL;
377 GSList* lines = NULL;
379 //CoreObject *o = NULL;
381 int rtn = -1 , status = 0;
383 dbg(" Func Entrance");
385 lines = (GSList *)event_info;
386 if (1 != g_slist_length(lines))
388 dbg("unsolicited msg but multiple line");
391 line = (char *)(lines->data);
393 dbg(" Func Entrance");
398 dbg("noti line is %s", line);
399 tokens = tcore_at_tok_new(line);
400 pResp = g_slist_nth_data(tokens, 0);
402 status = atoi(pResp);
410 if (status == AT_SMS_DEVICE_READY)
412 readyStatusInfo.status = SMS_DEVICE_READY;
413 tcore_sms_set_ready_status(o, readyStatusInfo.status);
414 dbg("SMS Ready status = [%s]", readyStatusInfo.status ? "TRUE" : "FALSE");
415 rtn = tcore_server_send_notification(tcore_plugin_ref_server(tcore_object_ref_plugin(o)), o, TNOTI_SMS_DEVICE_READY, sizeof(struct tnoti_sms_ready_status), &readyStatusInfo);
416 dbg(" Return value [%d]",rtn);
420 readyStatusInfo.status = SMS_DEVICE_NOT_READY;
425 tcore_at_tok_free(tokens);
429 static gboolean on_event_class2_sms_incom_msg(CoreObject *obj, const void *event_info, void *user_data)
431 //+CMTI: <mem>,<index>
433 GSList *tokens = NULL , *lines = NULL;
434 char *line = NULL, *cmd_str = NULL;
435 int index = 0, mem_type = 0;
436 TcoreHal *hal = NULL;
437 TcoreATRequest *atreq = NULL;
438 TcorePending *pending = NULL;
440 dbg("Entered Function");
442 lines = (GSList *)event_info;
443 line = (char *)g_slist_nth_data(lines, 0); /* Fetch Line 1 */
445 dbg("Line 1: [%s]", line);
449 err("Line 1 is invalid");
453 tokens = tcore_at_tok_new(line); /* Split Line 1 into tokens */
454 mem_type = atoi(g_slist_nth_data(tokens, 0)); //Type of Memory stored
455 index = atoi((char *)g_slist_nth_data(tokens, 1));
457 hal = tcore_object_get_hal(obj);
460 err("NULL input. Unable to proceed");
461 dbg("readMsg: hal: [%p]", hal);
464 return TCORE_RETURN_EINVAL;
467 dbg("index: [%d]", index);
469 cmd_str = g_strdup_printf("AT+CMGR=%d", index);
470 atreq = tcore_at_request_new((const char *)cmd_str, "+CMGR", TCORE_AT_PDU);
471 pending = tcore_pending_new(obj, 0);
473 if(NULL == cmd_str || NULL == atreq || NULL == pending)
475 err("Out of memory. Unable to proceed");
476 dbg("cmd_str: [%p], atreq: [%p], pending: [%p]", cmd_str, atreq, pending);
480 util_sms_free_memory(atreq);
481 util_sms_free_memory(pending);
484 return TCORE_RETURN_ENOMEM;
487 util_hex_dump(" ", strlen(cmd_str), (void *)cmd_str);
489 tcore_pending_set_request_data(pending, 0, atreq);
490 tcore_pending_set_response_callback(pending, on_response_class2_read_msg, (void *)(uintptr_t)index); //storing index as user data for response
491 tcore_pending_link_user_request(pending, NULL);
492 tcore_pending_set_send_callback(pending, on_confirmation_sms_message_send, NULL);
493 tcore_hal_send_request(hal, pending);
499 static gboolean on_event_sms_incom_msg(CoreObject *o, const void *event_info, void *user_data)
501 //+CMT: [<alpha>],<length><CR><LF><pdu> (PDU mode enabled);
504 GSList *tokens = NULL;
505 GSList *lines = NULL;
507 int length = 0, no_of_tokens = 0;
508 unsigned char *bytePDU = NULL;
509 struct tnoti_sms_umts_msg gsmMsgInfo;
511 dbg("Entered Function");
513 lines = (GSList *)event_info;
514 memset(&gsmMsgInfo, 0x00, sizeof(struct tnoti_sms_umts_msg));
516 if(2 != g_slist_length(lines))
518 err("Invalid number of lines for +CMT. Must be 2");
522 line = (char *)g_slist_nth_data(lines, 0); /* Fetch Line 1 */
524 dbg("Line 1: [%s]", line);
528 err("Line 1 is invalid");
532 tokens = tcore_at_tok_new(line); /* Split Line 1 into tokens */
534 no_of_tokens = g_slist_length(tokens);
536 if (no_of_tokens == 2) // in case of incoming SMS +CMT
538 dbg("Alpha ID: [%02x]", g_slist_nth_data(tokens, 0)); /* 0: Alpha ID */
539 length = atoi((char *)g_slist_nth_data(tokens, 1));
540 dbg("Length: [%d]", length); /* 1: PDU Length */
542 else if (no_of_tokens == 1) // in case of incoming status report +CDS
544 length = atoi((char *)g_slist_nth_data(tokens, 0));
545 dbg("Length: [%d]", length); /* 1: PDU Length */
548 gsmMsgInfo.msgInfo.msgLength = length;
550 line = (char *)g_slist_nth_data(lines, 1); /* Fetch Line 2 */
552 dbg("Line 2: [%s]", line);
556 err("Line 2 is invalid");
560 /* Convert to Bytes */
561 bytePDU = (unsigned char *)util_hexStringToBytes(line);
565 err("bytePDU is NULL");
569 memcpy(gsmMsgInfo.msgInfo.sca, bytePDU, (strlen(line)/2 - length));
570 memcpy(gsmMsgInfo.msgInfo.tpduData, &bytePDU[(strlen(line)/2 - length)], length);
572 util_hex_dump(" ", strlen(line)/2, bytePDU);
573 util_hex_dump(" ", (strlen(line)/2 - length), gsmMsgInfo.msgInfo.sca);
574 util_hex_dump(" ", length, gsmMsgInfo.msgInfo.tpduData);
576 rtn = tcore_server_send_notification(tcore_plugin_ref_server(tcore_object_ref_plugin(o)), o, TNOTI_SMS_INCOM_MSG, sizeof(struct tnoti_sms_umts_msg), &gsmMsgInfo);
583 static gboolean on_event_sms_memory_status(CoreObject *o, const void *event_info, void *user_data)
585 struct tnoti_sms_memory_status memStatusInfo = {0,};
587 int rtn = -1 ,memoryStatus = -1;
590 char *line = NULL , *pResp = NULL;
592 lines = (GSList *)event_info;
593 if (1 != g_slist_length(lines))
595 dbg("unsolicited msg but multiple line");
598 line = (char*)(lines->data);
601 dbg(" Func Entrance");
606 tokens = tcore_at_tok_new(line);
607 pResp = g_slist_nth_data(tokens, 0);
611 memoryStatus = atoi(pResp);
612 dbg("memoryStatus is %d",memoryStatus);
621 if (memoryStatus == 0) //SIM Full condition
623 memStatusInfo.status = SMS_PHONE_MEMORY_STATUS_FULL;
627 dbg("memory status - %d",memStatusInfo.status);
629 rtn = tcore_server_send_notification(tcore_plugin_ref_server(tcore_object_ref_plugin(o)), o, TNOTI_SMS_MEMORY_STATUS, sizeof(struct tnoti_sms_memory_status), &memStatusInfo);
630 dbg(" Return value [%d]",rtn);
635 static gboolean on_event_sms_cb_incom_msg(CoreObject *o, const void *event_info, void *user_data)
637 //+CBM: <length><CR><LF><pdu>
639 struct tnoti_sms_cellBroadcast_msg cbMsgInfo;
641 int rtn = -1 , length = 0;
642 char * line = NULL, *pdu = NULL, *pResp = NULL;
643 GSList *tokens = NULL;
644 GSList *lines = NULL;
646 dbg(" Func Entrance");
648 lines = (GSList *)event_info;
650 memset(&cbMsgInfo, 0, sizeof(struct tnoti_sms_cellBroadcast_msg));
652 line = (char *)(lines->data);
657 dbg("Noti line is %s",line);
658 tokens = tcore_at_tok_new(line); /* Split Line 1 into tokens */
660 pResp = g_slist_nth_data(tokens, 0);
662 length = atoi(pResp);
664 dbg("token 0 is null");
667 pdu = g_slist_nth_data(lines, 1);
670 cbMsgInfo.cbMsg.length = length/2;
671 cbMsgInfo.cbMsg.cbMsgType = SMS_CB_MSG_CBS ; //TODO - Need to check for other CB types
673 dbg("CB Msg LENGTH [%2x]", length);
675 if (cbMsgInfo.cbMsg.length >0)// && (SMS_CB_PAGE_SIZE_MAX >= cbMsgInfo.cbMsg.length))
677 unsigned char *byte_pdu = NULL;
679 byte_pdu = (unsigned char *)util_hexStringToBytes(pdu);
681 memcpy(cbMsgInfo.cbMsg.msgData, (char*)byte_pdu, cbMsgInfo.cbMsg.length);
682 rtn = tcore_server_send_notification(tcore_plugin_ref_server(tcore_object_ref_plugin(o)), o, TNOTI_SMS_CB_INCOM_MSG, sizeof(struct tnoti_sms_cellBroadcast_msg), &cbMsgInfo);
687 dbg("Invalid Message Length");
692 dbg("Recieved NULL pdu");
700 dbg(" Return value [%d]",rtn);
705 /*=============================================================
707 ==============================================================*/
708 static void on_response_sms_delete_msg(TcorePending *p, int data_len, const void *data, void *user_data)
710 struct tresp_sms_delete_msg delMsgInfo = {0,};
711 UserRequest *ur = NULL;
712 const TcoreATResponse *atResp = data;
715 int *index = (int *)user_data;
717 dbg(" Func Entrance");
719 ur = tcore_pending_ref_user_request(p);
723 delMsgInfo.index = *index;
724 delMsgInfo.result = SMS_SENDSMS_SUCCESS;
730 delMsgInfo.index = *index;
731 delMsgInfo.result = SMS_DEVICE_FAILURE;
735 rtn = tcore_user_request_send_response(ur, TRESP_SMS_DELETE_MSG, sizeof(struct tresp_sms_delete_msg), &delMsgInfo);
740 static void on_response_sms_save_msg(TcorePending *p, int data_len, const void *data, void *user_data)
742 struct tresp_sms_save_msg saveMsgInfo = {0,};
743 UserRequest *ur = NULL;
744 const TcoreATResponse *atResp = data;
745 GSList *tokens = NULL;
750 ur = tcore_pending_ref_user_request(p);
756 line = (char *)atResp->lines->data;
757 tokens = tcore_at_tok_new(line);
758 pResp = g_slist_nth_data(tokens, 0);
762 saveMsgInfo.index = (atoi(pResp) - 1); /* IMC index starts from 1 */
763 saveMsgInfo.result = SMS_SENDSMS_SUCCESS;
768 saveMsgInfo.index = -1;
769 saveMsgInfo.result = SMS_DEVICE_FAILURE;
777 saveMsgInfo.index = -1;
778 saveMsgInfo.result = SMS_DEVICE_FAILURE;
781 rtn = tcore_user_request_send_response(ur, TRESP_SMS_SAVE_MSG, sizeof(struct tresp_sms_save_msg), &saveMsgInfo);
782 dbg("Return value [%d]", rtn);
786 static void on_response_send_umts_msg(TcorePending *pending, int data_len, const void *data, void *user_data)
788 const TcoreATResponse *at_response = data;
789 struct tresp_sms_send_umts_msg resp_umts;
790 UserRequest *user_req = NULL;
793 GSList *tokens = NULL;
794 char *gslist_line = NULL, *line_token = NULL;
798 user_req = tcore_pending_ref_user_request(pending);
802 err("No user request");
808 memset(&resp_umts, 0x00, sizeof(resp_umts));
809 resp_umts.result = SMS_DEVICE_FAILURE;
811 if(at_response->success > 0) //success
814 if(at_response->lines) //lines present in at_response
816 gslist_line = (char *)at_response->lines->data;
817 dbg("gslist_line: [%s]", gslist_line);
819 tokens = tcore_at_tok_new(gslist_line); //extract tokens
821 line_token = g_slist_nth_data(tokens, 0);
822 if (line_token != NULL)
824 msg_ref = atoi(line_token);
825 dbg("Message Reference: [%d]", msg_ref);
827 resp_umts.result = SMS_SENDSMS_SUCCESS;
831 dbg("No Message Reference received");
834 else //no lines in at_response
844 tcore_user_request_send_response(user_req, TRESP_SMS_SEND_UMTS_MSG, sizeof(resp_umts), &resp_umts);
850 static void on_response_class2_read_msg(TcorePending *pending, int data_len, const void *data, void *user_data)
852 const TcoreATResponse *at_response = data;
854 char *gslist_line = NULL, *line_token = NULL, *hex_pdu = NULL;
855 int pdu_len = 0, rtn = 0;
856 unsigned char *bytePDU = NULL;
857 struct tnoti_sms_umts_msg gsmMsgInfo;
860 dbg("lines: [%p]", at_response->lines);
861 g_slist_foreach(at_response->lines, print_glib_list_elem, NULL); //for debug log
863 if (at_response->success > 0)
866 if (at_response->lines)
869 gslist_line = (char *)at_response->lines->data;
871 dbg("gslist_line: [%s]", gslist_line);
873 tokens = tcore_at_tok_new(gslist_line);
874 dbg("Number of tokens: [%d]", g_slist_length(tokens));
875 g_slist_foreach(tokens, print_glib_list_elem, NULL); //for debug log
877 line_token = g_slist_nth_data(tokens, 2); //Third Token: Length
878 if (line_token != NULL)
880 pdu_len = atoi(line_token);
881 dbg("Length: [%d]", pdu_len);
885 gslist_line = (char *)at_response->lines->next->data;
887 dbg("gslist_line: [%s]", gslist_line);
889 tokens = tcore_at_tok_new(gslist_line);
890 dbg("Number of tokens: [%d]", g_slist_length(tokens));
891 g_slist_foreach(tokens, print_glib_list_elem, NULL); //for debug log
893 hex_pdu = g_slist_nth_data(tokens, 0); //Fetch SMS PDU
906 gsmMsgInfo.msgInfo.msgLength = pdu_len;
909 /* Convert to Bytes */
910 bytePDU = (unsigned char *)util_hexStringToBytes(hex_pdu);
914 err("bytePDU is NULL");
918 memcpy(gsmMsgInfo.msgInfo.sca, bytePDU, (strlen(hex_pdu)/2 - pdu_len));
919 memcpy(gsmMsgInfo.msgInfo.tpduData, &bytePDU[(strlen(hex_pdu)/2 - pdu_len)], pdu_len);
921 util_hex_dump(" ", strlen(hex_pdu)/2, bytePDU);
922 util_hex_dump(" ", (strlen(hex_pdu)/2 - pdu_len), gsmMsgInfo.msgInfo.sca);
923 util_hex_dump(" ", pdu_len, gsmMsgInfo.msgInfo.tpduData);
925 rtn = tcore_server_send_notification(tcore_plugin_ref_server(tcore_object_ref_plugin(tcore_pending_ref_core_object(pending))), tcore_pending_ref_core_object(pending), TNOTI_SMS_INCOM_MSG, sizeof(struct tnoti_sms_umts_msg), &gsmMsgInfo);
932 static void on_response_read_msg(TcorePending *pending, int data_len, const void *data, void *user_data)
934 const TcoreATResponse *at_response = data;
935 struct tresp_sms_read_msg resp_read_msg;
936 UserRequest *user_req = NULL;
939 char *gslist_line = NULL, *line_token = NULL, *byte_pdu = NULL, *hex_pdu = NULL;
941 int msg_status = 0, alpha_id = 0, pdu_len = 0;
942 int index = (int)(uintptr_t)user_data;
945 dbg("index: [%d]", index);
946 dbg("lines: [%p]", at_response->lines);
947 g_slist_foreach(at_response->lines, print_glib_list_elem, NULL); //for debug log
949 user_req = tcore_pending_ref_user_request(pending);
950 if (NULL == user_req)
952 err("No user request");
958 memset(&resp_read_msg, 0x00, sizeof(resp_read_msg));
959 resp_read_msg.result = SMS_PHONE_FAILURE;
961 if (at_response->success > 0)
964 if (at_response->lines)
967 gslist_line = (char *)at_response->lines->data;
969 dbg("gslist_line: [%s]", gslist_line);
971 tokens = tcore_at_tok_new(gslist_line);
972 dbg("Number of tokens: [%d]", g_slist_length(tokens));
973 g_slist_foreach(tokens, print_glib_list_elem, NULL); //for debug log
975 line_token = g_slist_nth_data(tokens, 0); //First Token: Message Status
976 if (line_token != NULL)
978 msg_status = atoi(line_token);
979 dbg("msg_status is %d",msg_status);
983 resp_read_msg.dataInfo.msgStatus = SMS_STATUS_UNREAD;
987 resp_read_msg.dataInfo.msgStatus = SMS_STATUS_READ;
991 resp_read_msg.dataInfo.msgStatus = SMS_STATUS_UNSENT;
995 resp_read_msg.dataInfo.msgStatus = SMS_STATUS_SENT;
998 case AT_ALL: //Fall Through
999 default: //Fall Through
1000 resp_read_msg.dataInfo.msgStatus = SMS_STATUS_RESERVED;
1005 line_token = g_slist_nth_data(tokens, 1); //Second Token: AlphaID
1006 if (line_token != NULL)
1008 alpha_id = atoi(line_token);
1009 dbg("AlphaID: [%d]", alpha_id);
1012 line_token = g_slist_nth_data(tokens, 2); //Third Token: Length
1013 if (line_token != NULL)
1015 pdu_len = atoi(line_token);
1016 dbg("Length: [%d]", pdu_len);
1020 gslist_line = (char *)at_response->lines->next->data;
1022 dbg("gslist_line: [%s]", gslist_line);
1024 tokens = tcore_at_tok_new(gslist_line);
1025 dbg("Number of tokens: [%d]", g_slist_length(tokens));
1026 g_slist_foreach(tokens, print_glib_list_elem, NULL); //for debug log
1028 hex_pdu = g_slist_nth_data(tokens, 0); //Fetch SMS PDU
1029 if (NULL != hex_pdu)
1031 util_hex_dump(" ", sizeof(hex_pdu), (void *)hex_pdu);
1033 byte_pdu = util_hexStringToBytes(hex_pdu);
1035 sca_length = (int)byte_pdu[0];
1037 resp_read_msg.dataInfo.simIndex = index; //Retrieving index stored as user_data
1041 dbg("SCA Length is 0");
1043 resp_read_msg.dataInfo.smsData.msgLength = pdu_len - (sca_length+1);
1044 dbg("msgLength: [%d]", resp_read_msg.dataInfo.smsData.msgLength);
1046 if ((resp_read_msg.dataInfo.smsData.msgLength > 0)
1047 && (resp_read_msg.dataInfo.smsData.msgLength <= 0xff))
1049 memset(resp_read_msg.dataInfo.smsData.sca, 0, TAPI_SIM_SMSP_ADDRESS_LEN);
1050 memcpy(resp_read_msg.dataInfo.smsData.tpduData, &byte_pdu[2], resp_read_msg.dataInfo.smsData.msgLength);
1052 resp_read_msg.result = SMS_SUCCESS;
1056 err("Invalid Message Length");
1058 resp_read_msg.result = SMS_INVALID_PARAMETER_FORMAT;
1063 dbg("SCA Length : %d", sca_length);
1065 resp_read_msg.dataInfo.smsData.msgLength = (pdu_len - (sca_length+1));
1066 dbg("msgLength: [%d]", resp_read_msg.dataInfo.smsData.msgLength);
1068 if ((resp_read_msg.dataInfo.smsData.msgLength > 0)
1069 && (resp_read_msg.dataInfo.smsData.msgLength <= 0xff))
1071 memcpy(resp_read_msg.dataInfo.smsData.sca, (char *)byte_pdu, (sca_length+1));
1072 memcpy(resp_read_msg.dataInfo.smsData.tpduData, &byte_pdu[sca_length+1], resp_read_msg.dataInfo.smsData.msgLength);
1074 util_hex_dump(" ", SMS_SMSP_ADDRESS_LEN, (void *)resp_read_msg.dataInfo.smsData.sca);
1075 util_hex_dump(" ", (SMS_SMDATA_SIZE_MAX + 1), (void *)resp_read_msg.dataInfo.smsData.tpduData);
1076 util_hex_dump(" ", sizeof(byte_pdu), (void *)byte_pdu);
1078 resp_read_msg.result = SMS_SUCCESS;
1082 err("Invalid Message Length");
1083 resp_read_msg.result = SMS_INVALID_PARAMETER_FORMAT;
1099 err("Response NOK");
1102 tcore_user_request_send_response(user_req, TRESP_SMS_READ_MSG, sizeof(resp_read_msg), &resp_read_msg);
1108 static void on_response_get_msg_indices(TcorePending *pending, int data_len, const void *data, void *user_data)
1110 const TcoreATResponse *at_response = data;
1111 struct tresp_sms_get_storedMsgCnt resp_stored_msg_cnt;
1112 UserRequest *user_req = NULL;
1113 struct tresp_sms_get_storedMsgCnt *resp_stored_msg_cnt_prev = NULL;
1115 GSList *tokens = NULL;
1116 char *gslist_line = NULL, *line_token = NULL;
1117 int gslist_line_count = 0, ctr_loop = 0;
1121 resp_stored_msg_cnt_prev = (struct tresp_sms_get_storedMsgCnt *)user_data;
1122 user_req = tcore_pending_ref_user_request(pending);
1124 memset(&resp_stored_msg_cnt, 0x00, sizeof(resp_stored_msg_cnt));
1125 resp_stored_msg_cnt.result = SMS_DEVICE_FAILURE;
1127 if (at_response->success)
1130 if(at_response->lines)
1132 gslist_line_count = g_slist_length(at_response->lines);
1134 if (gslist_line_count > SMS_GSM_SMS_MSG_NUM_MAX)
1135 gslist_line_count = SMS_GSM_SMS_MSG_NUM_MAX;
1137 dbg("Number of lines: [%d]", gslist_line_count);
1138 g_slist_foreach(at_response->lines, print_glib_list_elem, NULL); //for debug log
1140 for (ctr_loop = 0; ctr_loop < gslist_line_count ; ctr_loop++)
1142 gslist_line = (char *)g_slist_nth_data(at_response->lines, ctr_loop); /* Fetch Line i */
1144 dbg("gslist_line [%d] is [%s]", ctr_loop, gslist_line);
1146 if (NULL != gslist_line)
1148 tokens = tcore_at_tok_new(gslist_line);
1150 g_slist_foreach(tokens, print_glib_list_elem, NULL); //for debug log
1152 line_token = g_slist_nth_data(tokens, 0);
1153 if (NULL != line_token)
1155 resp_stored_msg_cnt.storedMsgCnt.indexList[ctr_loop] = atoi(line_token);
1156 resp_stored_msg_cnt.result = SMS_SENDSMS_SUCCESS;
1160 dbg("line_token of gslist_line [%d] is NULL", ctr_loop);
1163 tcore_at_tok_free(tokens);
1167 dbg("gslist_line [%d] is NULL", ctr_loop);
1175 if(resp_stored_msg_cnt_prev->storedMsgCnt.usedCount == 0) //Check if used count is zero
1177 resp_stored_msg_cnt.result = SMS_SENDSMS_SUCCESS;
1183 dbg("Respnose NOK");
1186 resp_stored_msg_cnt.storedMsgCnt.totalCount = resp_stored_msg_cnt_prev->storedMsgCnt.totalCount;
1187 resp_stored_msg_cnt.storedMsgCnt.usedCount = resp_stored_msg_cnt_prev->storedMsgCnt.usedCount;
1189 util_sms_free_memory(resp_stored_msg_cnt_prev);
1191 dbg("total: [%d], used: [%d], result: [%d]", resp_stored_msg_cnt.storedMsgCnt.totalCount, resp_stored_msg_cnt.storedMsgCnt.usedCount, resp_stored_msg_cnt.result);
1192 for(ctr_loop = 0; ctr_loop < gslist_line_count; ctr_loop++)
1194 dbg("index: [%d]", resp_stored_msg_cnt.storedMsgCnt.indexList[ctr_loop]);
1197 tcore_user_request_send_response(user_req, TRESP_SMS_GET_STORED_MSG_COUNT, sizeof(resp_stored_msg_cnt), &resp_stored_msg_cnt);
1203 static void on_response_get_stored_msg_cnt(TcorePending *pending, int data_len, const void *data, void *user_data)
1205 UserRequest *ur = NULL, *ur_dup = NULL;
1206 struct tresp_sms_get_storedMsgCnt *respStoredMsgCnt = NULL;
1207 const TcoreATResponse *atResp = data;
1208 GSList *tokens=NULL;
1209 char *line = NULL , *pResp = NULL , *cmd_str = NULL;
1210 TcoreATRequest *atReq = NULL;
1211 int usedCnt = 0, totalCnt = 0, result = 0;
1213 TcorePending *pending_new = NULL;
1214 CoreObject *o = NULL;
1218 respStoredMsgCnt = malloc(sizeof(struct tresp_sms_get_storedMsgCnt));
1220 ur = tcore_pending_ref_user_request(pending);
1221 ur_dup = tcore_user_request_ref(ur);
1222 o = tcore_pending_ref_core_object(pending);
1224 if (atResp->success > 0)
1227 if(NULL != atResp->lines)
1229 line = (char *)atResp->lines->data;
1230 dbg("line is %s",line);
1232 tokens = tcore_at_tok_new(line);
1233 pResp = g_slist_nth_data(tokens, 0);
1237 usedCnt =atoi(pResp);
1238 dbg("used cnt is %d",usedCnt);
1241 pResp = g_slist_nth_data(tokens, 1);
1244 totalCnt =atoi(pResp);
1245 result = SMS_SENDSMS_SUCCESS;
1247 respStoredMsgCnt->storedMsgCnt.usedCount = usedCnt;
1248 respStoredMsgCnt->storedMsgCnt.totalCount = totalCnt;
1249 respStoredMsgCnt->result = result;
1251 dbg("used %d, total %d, result %d",usedCnt, totalCnt,result);
1253 pending_new = tcore_pending_new(o, 0);
1254 //Get all messages information
1255 cmd_str = g_strdup_printf("AT+CMGL=4");
1256 atReq = tcore_at_request_new((const char *)cmd_str, "+CMGL", TCORE_AT_MULTILINE);
1258 dbg("cmd str is %s",cmd_str);
1260 tcore_pending_set_request_data(pending_new, 0,atReq);
1261 tcore_pending_set_response_callback(pending_new, on_response_get_msg_indices, (void *)respStoredMsgCnt);
1262 tcore_pending_link_user_request(pending_new, ur_dup);
1263 tcore_pending_set_send_callback(pending_new, on_confirmation_sms_message_send, NULL);
1264 tcore_hal_send_request(tcore_object_get_hal(o), pending_new);
1275 result = SMS_DEVICE_FAILURE;
1279 err("Response NOK");
1285 static void on_response_get_sca(TcorePending *pending, int data_len, const void *data, void *user_data)
1287 const TcoreATResponse *at_response = data;
1288 struct tresp_sms_get_sca respGetSca;
1289 UserRequest *user_req = NULL;
1291 GSList *tokens = NULL;
1292 char *gslist_line = NULL, *sca_addr = NULL, *sca_toa = NULL;
1296 memset(&respGetSca, 0, sizeof(respGetSca));
1297 respGetSca.result = SMS_DEVICE_FAILURE;
1299 user_req = tcore_pending_ref_user_request(pending);
1301 if (at_response->success)
1304 if(at_response->lines)
1306 gslist_line = (char *)at_response->lines->data;
1308 tokens = tcore_at_tok_new(gslist_line);
1309 sca_addr = g_slist_nth_data(tokens, 0);
1310 sca_toa = g_slist_nth_data(tokens, 1);
1312 if ((NULL != sca_addr)
1313 && (NULL != sca_toa))
1315 dbg("sca_addr: [%s]. sca_toa: [%s]", sca_addr, sca_toa);
1317 respGetSca.scaAddress.dialNumLen = strlen(sca_addr);
1319 if(145 == atoi(sca_toa))
1321 respGetSca.scaAddress.typeOfNum = SIM_TON_INTERNATIONAL;
1325 respGetSca.scaAddress.typeOfNum = SIM_TON_NATIONAL;
1328 respGetSca.scaAddress.numPlanId = 0;
1330 memcpy(respGetSca.scaAddress.diallingNum, sca_addr, strlen(sca_addr));
1332 dbg("len [%d], sca_addr [%s], TON [%d], NPI [%d]", respGetSca.scaAddress.dialNumLen, respGetSca.scaAddress.diallingNum, respGetSca.scaAddress.typeOfNum, respGetSca.scaAddress.numPlanId);
1334 respGetSca.result = SMS_SENDSMS_SUCCESS;
1338 err("sca_addr OR sca_toa NULL");
1348 dbg("Response NOK");
1351 tcore_user_request_send_response(user_req, TRESP_SMS_GET_SCA, sizeof(respGetSca), &respGetSca);
1357 static void on_response_set_sca(TcorePending *pending, int data_len, const void *data, void *user_data)
1360 Response is expected in this format
1366 //CoreObject *obj = user_data;
1368 //copies the AT response data to resp
1369 const TcoreATResponse *atResp = data;
1370 struct tresp_sms_set_sca respSetSca;
1372 memset(&respSetSca, 0, sizeof(struct tresp_sms_set_sca));
1374 ur = tcore_pending_ref_user_request(pending);
1377 dbg("no user_request");
1381 if (atResp->success >0)
1384 respSetSca.result = SMS_SUCCESS;
1388 dbg("RESPONSE NOK");
1389 respSetSca.result = SMS_DEVICE_FAILURE;
1392 tcore_user_request_send_response(ur, TRESP_SMS_SET_SCA, sizeof(struct tresp_sms_set_sca), &respSetSca);
1397 static void on_response_get_cb_config(TcorePending *p, int data_len, const void *data, void *user_data)
1400 struct tresp_sms_get_cb_config respGetCbConfig;
1401 const TcoreATResponse *atResp = data;
1402 GSList *tokens=NULL;
1405 char *mid = NULL, *pResp = NULL, *line = NULL, *res = NULL;
1408 memset(&respGetCbConfig, 0, sizeof(struct tresp_sms_get_cb_config));
1409 respGetCbConfig.result = SMS_DEVICE_FAILURE;
1411 ur = tcore_pending_ref_user_request(p);
1414 dbg("no user_request");
1418 if (atResp->success)
1423 line = (char*)atResp->lines->data;
1426 dbg("line is %s",line);
1427 tokens = tcore_at_tok_new(line);
1428 pResp = g_slist_nth_data(tokens, 0);
1432 respGetCbConfig.cbConfig.bCBEnabled = mode;
1434 respGetCbConfig.result = SMS_SENDSMS_SUCCESS;
1436 pResp = g_slist_nth_data(tokens, 1);
1439 mid = strtok(pResp, delim); i = 0;
1440 while( res != NULL )
1442 res = strtok( NULL, delim );
1443 dbg("mid is %s%s\n", mid,res);
1448 respGetCbConfig.cbConfig.msgIDs[i] = atoi(res);
1454 respGetCbConfig.cbConfig.msgIdCount = i;
1456 //dcs = g_slist_nth_data(tokens, 2); DCS not needed by telephony
1460 dbg("line is NULL");
1465 dbg("atresp->lines is NULL");
1470 dbg("RESPONSE NOK");
1473 tcore_user_request_send_response(ur, TRESP_SMS_GET_CB_CONFIG, sizeof(struct tresp_sms_get_cb_config), &respGetCbConfig);
1478 static void on_response_set_cb_config(TcorePending *pending, int data_len, const void *data, void *user_data)
1481 Response is expected in this format
1488 const TcoreATResponse *resp = data;
1490 const char *line = NULL;
1491 GSList *tokens=NULL;
1493 struct tresp_sms_set_cb_config respSetCbConfig = {0,};
1495 memset(&respSetCbConfig, 0, sizeof(struct tresp_sms_set_cb_config));
1497 ur = tcore_pending_ref_user_request(pending);
1498 respSetCbConfig.result = SMS_SENDSMS_SUCCESS;
1500 if(resp->success > 0)
1507 dbg("RESPONSE NOK");
1508 line = (const char*)resp->final_response;
1509 tokens = tcore_at_tok_new(line);
1511 if (g_slist_length(tokens) < 1) {
1512 dbg("err cause not specified or string corrupted");
1513 respSetCbConfig.result = SMS_DEVICE_FAILURE;
1517 response = atoi(g_slist_nth_data(tokens, 0));
1518 /* TODO: CMEE error mapping is required. */
1519 respSetCbConfig.result = SMS_DEVICE_FAILURE;
1524 dbg("no user_request");
1528 tcore_user_request_send_response(ur, TRESP_SMS_SET_CB_CONFIG, sizeof(struct tresp_sms_set_cb_config), &respSetCbConfig);
1533 static void on_response_set_mem_status(TcorePending *p, int data_len, const void *data, void *user_data)
1536 struct tresp_sms_set_mem_status respSetMemStatus = {0,};
1537 const TcoreATResponse *resp = data;
1539 memset(&respSetMemStatus, 0, sizeof(struct tresp_sms_set_mem_status));
1541 if(resp->success > 0)
1544 respSetMemStatus.result = SMS_SENDSMS_SUCCESS;
1549 dbg("RESPONSE NOK");
1550 respSetMemStatus.result = SMS_DEVICE_FAILURE;
1553 ur = tcore_pending_ref_user_request(p);
1556 dbg("no user_request");
1560 tcore_user_request_send_response(ur, TRESP_SMS_SET_MEM_STATUS, sizeof(struct tresp_sms_set_mem_status), &respSetMemStatus);
1565 static void on_response_set_msg_status(TcorePending *pending, int data_len, const void *data, void *user_data)
1568 struct tresp_sms_set_msg_status respMsgStatus = {0,};
1569 const TcoreATResponse *atResp = data;
1570 int response = 0, sw1 =0 , sw2 = 0;
1571 const char *line = NULL;
1573 GSList *tokens=NULL;
1577 memset(&respMsgStatus, 0, sizeof(struct tresp_sms_set_msg_status));
1578 respMsgStatus.result = SMS_DEVICE_FAILURE;
1580 ur = tcore_pending_ref_user_request(pending);
1582 if(atResp->success > 0)
1588 line = (const char*)atResp->lines->data;
1589 tokens = tcore_at_tok_new(line);
1590 pResp = g_slist_nth_data(tokens, 0);
1599 pResp = g_slist_nth_data(tokens, 1);
1603 if ((sw1 == AT_SW1_SUCCESS) && (sw2 == 0))
1605 respMsgStatus.result = SMS_SENDSMS_SUCCESS;
1612 pResp = g_slist_nth_data(tokens, 3);
1616 response = atoi(pResp);
1617 dbg("response is %s", response);
1628 dbg("RESPONSE NOK");
1631 tcore_user_request_send_response(ur, TRESP_SMS_SET_MSG_STATUS , sizeof(struct tresp_sms_set_msg_status), &respMsgStatus);
1634 tcore_at_tok_free(tokens);
1640 static void on_response_get_sms_params(TcorePending *pending, int data_len, const void *data, void *user_data)
1643 struct tresp_sms_get_params respGetParams;
1644 const TcoreATResponse *atResp = data;
1645 int sw1 =0 , sw2 = 0;
1646 const char *line = NULL;
1648 GSList *tokens=NULL;
1649 char *hexData = NULL;
1650 char *recordData = NULL;
1653 memset(&respGetParams, 0, sizeof(struct tresp_sms_set_params));
1654 respGetParams.result = SMS_DEVICE_FAILURE;
1656 ur = tcore_pending_ref_user_request(pending);
1658 if(atResp->success > 0)
1664 line = (const char*)atResp->lines->data;
1665 tokens = tcore_at_tok_new(line);
1666 pResp = g_slist_nth_data(tokens, 0);
1670 dbg("sw1 is %d",sw1);
1676 pResp = g_slist_nth_data(tokens, 1);
1680 dbg("sw2 is %d",sw2);
1681 if ((sw1 == 0x90 && sw2 == 0x00) || sw1 == 0x91)
1683 respGetParams.result = SMS_SENDSMS_SUCCESS;
1690 pResp = g_slist_nth_data(tokens, 2);
1693 hexData = util_removeQuotes(pResp);
1695 recordData = util_hexStringToBytes(hexData);
1696 util_hex_dump(" ", strlen(hexData)/2, recordData);
1698 respGetParams.paramsInfo.recordLen = strlen(hexData)/2;
1700 util_sms_decode_smsParameters((unsigned char *)recordData , strlen(hexData)/2 , &(respGetParams.paramsInfo));
1701 respGetParams.result = SMS_SENDSMS_SUCCESS;
1703 for(i = 0 ; i < (int)respGetParams.paramsInfo.tpSvcCntrAddr.dialNumLen ; i ++)
1704 dbg("SCAddr = %d [%02x]",i,respGetParams.paramsInfo.tpSvcCntrAddr.diallingNum[i]);
1713 tcore_at_tok_free(tokens);
1718 dbg("RESPONSE NOK");
1721 tcore_user_request_send_response(ur, TRESP_SMS_GET_PARAMS, sizeof(struct tresp_sms_get_params), &respGetParams);
1727 static void on_response_set_sms_params(TcorePending *pending, int data_len, const void *data, void *user_data)
1730 struct tresp_sms_set_params respSetParams = {0,};
1731 const TcoreATResponse *atResp = data;
1732 int sw1 =0 , sw2 = 0;
1733 const char *line = NULL;
1735 GSList *tokens=NULL;
1738 memset(&respSetParams, 0, sizeof(struct tresp_sms_set_params));
1739 ur = tcore_pending_ref_user_request(pending);
1741 respSetParams.result = SMS_DEVICE_FAILURE;
1743 if(atResp->success > 0)
1749 line = (const char*)atResp->lines->data;
1750 tokens = tcore_at_tok_new(line);
1751 pResp = g_slist_nth_data(tokens, 0);
1752 if (pResp != NULL) {
1759 pResp = g_slist_nth_data(tokens, 1);
1763 if (((sw1 == AT_SW1_SUCCESS) && (sw2 == AT_SW2_SUCCESS)) || (sw1 == 0x91)){
1764 respSetParams.result = SMS_SENDSMS_SUCCESS;
1779 dbg("RESPONSE NOK");
1782 tcore_user_request_send_response(ur, TRESP_SMS_SET_PARAMS , sizeof(struct tresp_sms_set_params), &respSetParams);
1785 tcore_at_tok_free(tokens);
1791 static void on_response_get_paramcnt(TcorePending *p, int data_len, const void *data, void *user_data)
1794 UserRequest *ur = NULL;
1795 struct tresp_sms_get_paramcnt respGetParamCnt = {0,};
1796 const TcoreATResponse *atResp = data;
1797 char *line = NULL , *pResp = NULL;
1798 int sw1 = 0 , sw2 = 0, *smsp_record_len = NULL;
1800 GSList *tokens=NULL;
1801 CoreObject *co_sim = NULL; //need this to get the sim type GSM/USIM
1802 TcorePlugin *plugin = NULL;
1806 ur = tcore_pending_ref_user_request(p);
1807 respGetParamCnt.result = SMS_DEVICE_FAILURE;
1809 if(atResp->success > 0)
1815 line = (char*)atResp->lines->data;
1817 dbg("line is %s",line);
1819 tokens = tcore_at_tok_new(line);
1820 pResp = g_slist_nth_data(tokens, 0);
1829 pResp = g_slist_nth_data(tokens, 1);
1833 if ((sw1 == 144) && (sw2 == 0))
1835 respGetParamCnt.result = SMS_SENDSMS_SUCCESS;
1842 pResp = g_slist_nth_data(tokens, 2);
1845 char *hexData = NULL;
1846 char *recordData = NULL;
1847 hexData = util_removeQuotes(pResp);
1849 /*1. SIM access success case*/
1850 if ((sw1 == 0x90 && sw2 == 0x00) || sw1 == 0x91)
1852 unsigned char tag_len = 0; /* 1 or 2 bytes ??? */
1854 char num_of_records = 0;
1855 unsigned char file_id_len = 0;
1856 unsigned short file_id = 0;
1857 unsigned short file_size = 0;
1858 unsigned short file_type = 0;
1859 unsigned short arr_file_id = 0;
1860 int arr_file_id_rec_num = 0;
1862 /* handling only last 3 bits */
1863 unsigned char file_type_tag = 0x07;
1864 unsigned char *ptr_data;
1866 recordData = util_hexStringToBytes(hexData);
1867 util_hex_dump(" ", strlen(hexData)/2, recordData);
1869 ptr_data = (unsigned char *)recordData;
1871 co_sim = tcore_plugin_ref_core_object(tcore_pending_ref_plugin(p), "sim");
1872 sim_type = tcore_sim_get_type(co_sim);
1873 dbg("sim type is %d",sim_type);
1875 if (sim_type == SIM_TYPE_USIM) {
1877 ETSI TS 102 221 v7.9.0
1879 '62' FCP template tag
1880 - Response for an EF
1881 '82' M File Descriptor
1882 '83' M File Identifier
1883 'A5' O Proprietary information
1884 '8A' M Life Cycle Status Integer
1885 '8B', '8C' or 'AB' C1 Security attributes
1887 '81' O Total file size
1888 '88' O Short File Identifier (SFI)
1891 /* rsim.res_len has complete data length received */
1893 /* FCP template tag - File Control Parameters tag*/
1894 if (*ptr_data == 0x62) {
1895 /* parse complete FCP tag*/
1896 /* increment to next byte */
1898 tag_len = *ptr_data++;
1899 /* FCP file descriptor - file type, accessibility, DF, ADF etc*/
1900 if (*ptr_data == 0x82) {
1901 /* increment to next byte */
1905 /* unsigned char file_desc_len = *ptr_data++;*/
1906 /* dbg("file descriptor length: [%d]", file_desc_len);*/
1907 /* TBD: currently capture only file type : ignore sharable, non sharable, working, internal etc*/
1908 /* consider only last 3 bits*/
1909 file_type_tag = file_type_tag & (*ptr_data);
1911 switch (file_type_tag) {
1912 /* increment to next byte */
1915 dbg("Getting FileType: [Transparent file type]");
1916 /* increment to next byte */
1918 file_type = 0x01; //SIM_FTYPE_TRANSPARENT
1919 /* data coding byte - value 21 */
1924 dbg("Getting FileType: [Linear fixed file type]");
1925 /* increment to next byte */
1927 /* data coding byte - value 21 */
1930 memcpy(&record_len, ptr_data, 2);
1932 record_len = SMS_SWAPBYTES16(record_len);
1933 ptr_data = ptr_data + 2;
1934 num_of_records = *ptr_data++;
1935 /* Data lossy conversation from enum (int) to unsigned char */
1936 file_type = 0x02; // SIM_FTYPE_LINEAR_FIXED
1940 dbg(" Cyclic fixed file type");
1941 /* increment to next byte */
1943 /* data coding byte - value 21 */
1946 memcpy(&record_len, ptr_data, 2);
1948 record_len = SMS_SWAPBYTES16(record_len);
1949 ptr_data = ptr_data + 2;
1950 num_of_records = *ptr_data++;
1951 file_type = 0x04; //SIM_FTYPE_CYCLIC
1955 dbg("not handled file type [0x%x]", *ptr_data);
1961 dbg("INVALID FCP received - DEbug!");
1965 /*File identifier - file id?? */ // 0x84,0x85,0x86 etc are currently ignored and not handled
1966 if (*ptr_data == 0x83) {
1967 /* increment to next byte */
1969 file_id_len = *ptr_data++;
1970 memcpy(&file_id, ptr_data, file_id_len);
1972 file_id = SMS_SWAPBYTES16(file_id);
1973 ptr_data = ptr_data + 2;
1974 dbg("Getting FileID=[0x%x]", file_id);
1976 dbg("INVALID FCP received - DEbug!");
1979 //ReleaseResponse();
1983 /* proprietary information */
1984 if (*ptr_data == 0xA5) {
1985 unsigned short prop_len;
1986 /* increment to next byte */
1989 prop_len = *ptr_data;
1991 ptr_data = ptr_data + prop_len + 1;
1993 dbg("INVALID FCP received - DEbug!");
1996 /* life cycle status integer [8A][length:0x01][status]*/
1999 00000000 : No information given
2000 00000001 : creation state
2001 00000011 : initialization state
2002 000001-1 : operation state -activated
2003 000001-0 : operation state -deactivated
2004 000011-- : Termination state
2005 b8~b5 !=0, b4~b1=X : Proprietary
2006 Any other value : RFU
2008 if (*ptr_data == 0x8A) {
2009 /* increment to next byte */
2011 /* length - value 1 */
2014 switch (*ptr_data) {
2017 dbg("<IPC_RX> operation state -deactivated");
2022 dbg("<IPC_RX> operation state -activated");
2026 dbg("<IPC_RX> DEBUG! LIFE CYCLE STATUS =[0x%x]",*ptr_data);
2032 /* related to security attributes : currently not handled*/
2033 if (*ptr_data == 0x86 || *ptr_data == 0x8B || *ptr_data == 0x8C || *ptr_data == 0xAB) {
2034 /* increment to next byte */
2036 /* if tag length is 3 */
2037 if (*ptr_data == 0x03) {
2038 /* increment to next byte */
2041 memcpy(&arr_file_id, ptr_data, 2);
2043 arr_file_id = SMS_SWAPBYTES16(arr_file_id);
2044 ptr_data = ptr_data + 2;
2045 arr_file_id_rec_num = *ptr_data++;
2047 /* if tag length is not 3 */
2048 /* ignoring bytes */
2049 // ptr_data = ptr_data + 4;
2050 dbg("Useless security attributes, so jump to next tag");
2051 ptr_data = ptr_data + (*ptr_data + 1);
2054 dbg("INVALID FCP received[0x%x] - DEbug!", *ptr_data);
2061 dbg("Current ptr_data value is [%x]", *ptr_data);
2063 /* file size excluding structural info*/
2064 if (*ptr_data == 0x80) {
2065 /* for EF file size is body of file and for Linear or cyclic it is
2066 * number of recXsizeof(one record)
2068 /* increment to next byte */
2070 /* length is 1 byte - value is 2 bytes or more */
2072 memcpy(&file_size, ptr_data, 2);
2074 file_size = SMS_SWAPBYTES16(file_size);
2075 ptr_data = ptr_data + 2;
2077 dbg("INVALID FCP received - DEbug!");
2083 /* total file size including structural info*/
2084 if (*ptr_data == 0x81) {
2086 /* increment to next byte */
2091 ptr_data = ptr_data + 3;
2093 dbg("INVALID FCP received - DEbug!");
2094 /* 0x81 is optional tag?? check out! so do not return -1 from here! */
2097 /*short file identifier ignored*/
2098 if (*ptr_data == 0x88) {
2099 dbg("0x88: Do Nothing");
2103 dbg("INVALID FCP received - DEbug!");
2109 else if (sim_type == SIM_TYPE_GSM)
2111 unsigned char gsm_specific_file_data_len = 0;
2112 /* ignore RFU byte1 and byte2 */
2116 //file_size = p_info->response_len;
2117 memcpy(&file_size, ptr_data, 2);
2119 file_size = SMS_SWAPBYTES16(file_size);
2120 /* parsed file size */
2121 ptr_data = ptr_data + 2;
2123 memcpy(&file_id, ptr_data, 2);
2124 file_id = SMS_SWAPBYTES16(file_id);
2125 dbg(" FILE id --> [%x]", file_id);
2126 ptr_data = ptr_data + 2;
2127 /* save file type - transparent, linear fixed or cyclic */
2128 file_type_tag = (*(ptr_data + 7));
2130 switch (*ptr_data) {
2133 dbg(" RFU file type- not handled - Debug!");
2137 dbg(" MF file type - not handled - Debug!");
2141 dbg(" DF file type - not handled - Debug!");
2145 dbg(" EF file type [%d] ", file_type_tag);
2146 /* increment to next byte */
2149 if (file_type_tag == 0x00 || file_type_tag == 0x01) {
2150 /* increament to next byte as this byte is RFU */
2153 (file_type_tag == 0x00) ? 0x01 : 0x02; // SIM_FTYPE_TRANSPARENT:SIM_FTYPE_LINEAR_FIXED;
2155 /* increment to next byte */
2157 /* For a cyclic EF all bits except bit 7 are RFU; b7=1 indicates that */
2158 /* the INCREASE command is allowed on the selected cyclic file. */
2159 file_type = 0x04; // SIM_FTYPE_CYCLIC;
2161 /* bytes 9 to 11 give SIM file access conditions */
2163 /* byte 10 has one nibble that is RF U and another for INCREASE which is not used currently */
2165 /* byte 11 is invalidate and rehabilate nibbles */
2167 /* byte 12 - file status */
2169 /* byte 13 - GSM specific data */
2170 gsm_specific_file_data_len = *ptr_data;
2172 /* byte 14 - structure of EF - transparent or linear or cyclic , already saved above */
2174 /* byte 15 - length of record for linear and cyclic , for transparent it is set to 0x00. */
2175 record_len = *ptr_data;
2176 dbg("record length[%d], file size[%d]", record_len, file_size);
2178 if (record_len != 0)
2179 num_of_records = (file_size / record_len);
2181 dbg("Number of records [%d]", num_of_records);
2185 dbg(" not handled file type");
2191 dbg(" Card Type - UNKNOWN [%d]", sim_type);
2194 dbg("EF[0x%x] size[%ld] Type[0x%x] NumOfRecords[%ld] RecordLen[%ld]", file_id, file_size, file_type, num_of_records, record_len);
2196 respGetParamCnt.recordCount = num_of_records;
2197 respGetParamCnt.result = SMS_SUCCESS;
2199 //TO Store smsp record length in the property
2200 plugin = tcore_pending_ref_plugin(p);
2201 smsp_record_len = tcore_plugin_ref_property(plugin, "SMSPRECORDLEN");
2202 memcpy(smsp_record_len, &record_len, sizeof(int));
2209 /*2. SIM access fail case*/
2210 dbg("SIM access fail");
2211 respGetParamCnt.result = SMS_UNKNOWN;
2216 dbg("presp is NULL");
2221 dbg("line is blank");
2226 dbg("RESPONSE NOK");
2230 tcore_user_request_send_response(ur, TRESP_SMS_GET_PARAMCNT, sizeof(struct tresp_sms_get_paramcnt), &respGetParamCnt);
2236 static void _response_get_efsms_data(TcorePending *p, int data_len, const void *data, void *user_data)
2238 UserRequest *ur = NULL;
2239 UserRequest *dup_ur = NULL;
2240 struct tresp_sms_set_msg_status resp_msg_status = {0,};
2241 const struct treq_sms_set_msg_status *req_msg_status = NULL ;
2243 const TcoreATResponse *resp = data;
2244 char *encoded_data = NULL;
2245 char msg_status = 0;
2247 GSList *tokens=NULL;
2248 const char *line = NULL;
2252 TcoreHal *hal = NULL;
2253 TcoreATRequest *atreq = NULL;
2254 TcorePending *pending = NULL;
2255 gchar *cmd_str = NULL;
2257 ur = tcore_pending_ref_user_request(p);
2259 req_msg_status = tcore_user_request_ref_data(ur, NULL);
2261 resp_msg_status.result = SMS_DEVICE_FAILURE;
2263 hal = tcore_object_get_hal(tcore_pending_ref_core_object(pending));
2264 dbg("msgStatus: [%x], index [%x]", req_msg_status->msgStatus, req_msg_status->index);
2266 if(resp->success <= 0)
2275 line = (const char*)resp->lines->data;
2276 tokens = tcore_at_tok_new(line);
2277 if (g_slist_length(tokens) != 3)
2279 msg("invalid message");
2283 sw1 = atoi(g_slist_nth_data(tokens, 0));
2284 sw2 = atoi(g_slist_nth_data(tokens, 1));
2285 pResp = g_slist_nth_data(tokens, 2);
2287 if((sw1 == 0x90 && sw2 == 0x00) || sw1 == 0x91)
2289 switch (req_msg_status->msgStatus)
2291 case SMS_STATUS_READ:
2295 case SMS_STATUS_UNREAD:
2299 case SMS_STATUS_UNSENT:
2303 case SMS_STATUS_SENT:
2307 case SMS_STATUS_DELIVERED:
2311 case SMS_STATUS_DELIVERY_UNCONFIRMED:
2315 case SMS_STATUS_MESSAGE_REPLACED:
2316 case SMS_STATUS_RESERVED:
2322 encoded_data = util_removeQuotes(pResp);
2324 //overwrite Status byte information
2325 util_byte_to_hex((const char *)&msg_status, (char *)encoded_data, 1);
2327 //Update EF-SMS with just status byte overwritten, rest 175 bytes are same as received in read information
2328 cmd_str = g_strdup_printf("AT+CRSM=220,28476,%d, 4, %d, \"%s\"", (req_msg_status->index+1), AT_EF_SMS_RECORD_LEN, encoded_data);
2329 atreq = tcore_at_request_new((const char *)cmd_str, "+CRSM", TCORE_AT_SINGLELINE);
2330 pending = tcore_pending_new(tcore_pending_ref_core_object(pending), 0);
2331 if(NULL == cmd_str || NULL == atreq || NULL == pending)
2333 err("Out of memory. Unable to proceed");
2334 dbg("cmd_str: [%p], atreq: [%p], pending: [%p]", cmd_str, atreq, pending);
2336 //free memory we own
2339 util_sms_free_memory(atreq);
2340 util_sms_free_memory(pending);
2345 util_hex_dump(" ", strlen(cmd_str), (void *)cmd_str);
2347 dup_ur = tcore_user_request_ref(ur);
2349 tcore_pending_set_request_data(pending, 0, atreq);
2350 tcore_pending_set_response_callback(pending, on_response_set_msg_status, NULL);
2351 tcore_pending_link_user_request(pending, dup_ur);
2352 tcore_pending_set_send_callback(pending, on_confirmation_sms_message_send, NULL);
2353 tcore_hal_send_request(hal, pending);
2362 tcore_at_tok_free(tokens);
2364 tcore_user_request_send_response(ur, TRESP_SMS_SET_MSG_STATUS , sizeof(struct tresp_sms_set_msg_status), &msg_status);
2371 /*=============================================================
2373 ==============================================================*/
2374 static TReturn send_umts_msg(CoreObject *obj, UserRequest *ur)
2376 gchar *cmd_str = NULL;
2377 TcoreHal *hal = NULL;
2378 TcoreATRequest *atreq = NULL;
2379 TcorePending *pending = NULL;
2380 const struct treq_sms_send_umts_msg *sendUmtsMsg = NULL;
2381 char buf[2*(SMS_SMSP_ADDRESS_LEN+SMS_SMDATA_SIZE_MAX)+1] = {0};
2387 sendUmtsMsg = tcore_user_request_ref_data(ur, NULL);
2388 hal = tcore_object_get_hal(obj);
2389 if(NULL == sendUmtsMsg || NULL == hal)
2391 err("NULL input. Unable to proceed");
2392 dbg("sendUmtsMsg: [%p], hal: [%p]", sendUmtsMsg, hal);
2395 return TCORE_RETURN_EINVAL;
2398 dbg("msgLength: [%d]", sendUmtsMsg->msgDataPackage.msgLength);
2399 util_hex_dump(" ", (SMS_SMDATA_SIZE_MAX+1), (void *)sendUmtsMsg->msgDataPackage.tpduData);
2400 util_hex_dump(" ", SMS_SMSP_ADDRESS_LEN, (void *)sendUmtsMsg->msgDataPackage.sca);
2402 ScLength = (int)sendUmtsMsg->msgDataPackage.sca[0];
2404 dbg("ScLength: [%d]", ScLength);
2406 if ((sendUmtsMsg->msgDataPackage.msgLength > 0)
2407 && (sendUmtsMsg->msgDataPackage.msgLength <= SMS_SMDATA_SIZE_MAX)
2408 && (ScLength <= SMS_MAX_SMS_SERVICE_CENTER_ADDR))
2410 if(ScLength == 0) //ScAddress not specified
2418 dbg("Specifying SCA in TPDU is currently not supported");
2425 util_byte_to_hex((const char *)sendUmtsMsg->msgDataPackage.tpduData, (char *)&buf[pdu_len], sendUmtsMsg->msgDataPackage.msgLength);
2427 pdu_len = pdu_len + 2*sendUmtsMsg->msgDataPackage.msgLength;
2429 buf[pdu_len] = '\0'; //Ensure termination
2431 dbg("pdu_len: [%d]", pdu_len);
2432 util_hex_dump(" ", sizeof(buf), (void *)buf);
2434 //AT+CMGS=<length><CR>PDU is given<ctrl-Z/ESC>
2435 cmd_str = g_strdup_printf("AT+CMGS=%d%s%s\x1A", sendUmtsMsg->msgDataPackage.msgLength,"\r",buf);
2436 atreq = tcore_at_request_new((const char *)cmd_str, "+CMGS", TCORE_AT_SINGLELINE);
2437 pending = tcore_pending_new(obj, 0);
2439 if(NULL == cmd_str || NULL == atreq || NULL == pending)
2441 err("Out of memory. Unable to proceed");
2442 dbg("cmd_str: [%p], atreq: [%p], pending: [%p]", cmd_str, atreq, pending);
2444 //free memory we own
2446 util_sms_free_memory(atreq);
2447 util_sms_free_memory(pending);
2450 return TCORE_RETURN_ENOMEM;
2453 util_hex_dump(" ", strlen(cmd_str), (void *)cmd_str);
2455 tcore_pending_set_request_data(pending, 0, atreq);
2456 tcore_pending_set_response_callback(pending, on_response_send_umts_msg, NULL);
2457 tcore_pending_link_user_request(pending, ur);
2458 tcore_pending_set_send_callback(pending, on_confirmation_sms_message_send, NULL);
2459 tcore_hal_send_request(hal, pending);
2464 return TCORE_RETURN_SUCCESS;
2467 err("Invalid Data len");
2469 return TCORE_RETURN_SMS_INVALID_DATA_LEN;
2472 static TReturn read_msg(CoreObject *obj, UserRequest *ur)
2474 gchar *cmd_str = NULL;
2475 TcoreHal *hal = NULL;
2476 TcoreATRequest *atreq = NULL;
2477 TcorePending *pending = NULL;
2478 const struct treq_sms_read_msg *readMsg = NULL;
2482 readMsg = tcore_user_request_ref_data(ur, NULL);
2483 hal = tcore_object_get_hal(obj);
2484 if(NULL == readMsg || NULL == hal)
2486 err("NULL input. Unable to proceed");
2487 dbg("readMsg: [%p], hal: [%p]", readMsg, hal);
2490 return TCORE_RETURN_EINVAL;
2493 dbg("index: [%d]", readMsg->index);
2495 cmd_str = g_strdup_printf("AT+CMGR=%d", (readMsg->index + 1)); //IMC index is one ahead of TAPI
2496 atreq = tcore_at_request_new((const char *)cmd_str, "+CMGR", TCORE_AT_PDU);
2497 pending = tcore_pending_new(obj, 0);
2499 if(NULL == cmd_str || NULL == atreq || NULL == pending)
2501 err("Out of memory. Unable to proceed");
2502 dbg("cmd_str: [%p], atreq: [%p], pending: [%p]", cmd_str, atreq, pending);
2504 //free memory we own
2506 util_sms_free_memory(atreq);
2507 util_sms_free_memory(pending);
2510 return TCORE_RETURN_ENOMEM;
2513 util_hex_dump(" ", strlen(cmd_str), (void *)cmd_str);
2515 tcore_pending_set_request_data(pending, 0, atreq);
2516 tcore_pending_set_response_callback(pending, on_response_read_msg, (void *)(uintptr_t)(readMsg->index)); //storing index as user data for response
2517 tcore_pending_link_user_request(pending, ur);
2518 tcore_pending_set_send_callback(pending, on_confirmation_sms_message_send, NULL);
2519 tcore_hal_send_request(hal, pending);
2524 return TCORE_RETURN_SUCCESS;
2527 static TReturn save_msg(CoreObject *obj, UserRequest *ur)
2529 gchar *cmd_str = NULL;
2530 TcoreHal *hal = NULL;
2531 TcoreATRequest *atreq = NULL;
2532 TcorePending *pending = NULL;
2533 const struct treq_sms_save_msg *saveMsg = NULL;
2534 int ScLength = 0, pdu_len = 0, stat = 0;
2535 char buf[2*(SMS_SMSP_ADDRESS_LEN+SMS_SMDATA_SIZE_MAX)+1] = {0};
2539 saveMsg = tcore_user_request_ref_data(ur, NULL);
2540 hal = tcore_object_get_hal(obj);
2541 if(NULL == saveMsg || NULL == hal)
2543 err("NULL input. Unable to proceed");
2544 dbg("saveMsg: [%p], hal: [%p]", saveMsg, hal);
2547 return TCORE_RETURN_EINVAL;
2550 dbg("msgStatus: %x, msgLength: [%d]", saveMsg->msgStatus, saveMsg->msgDataPackage.msgLength);
2551 util_hex_dump(" ", (SMS_SMDATA_SIZE_MAX+1), (void *)saveMsg->msgDataPackage.tpduData);
2552 util_hex_dump(" ", SMS_SMSP_ADDRESS_LEN, (void *)saveMsg->msgDataPackage.sca);
2554 switch (saveMsg->msgStatus) {
2555 case SMS_STATUS_READ:
2559 case SMS_STATUS_UNREAD:
2560 stat = AT_REC_UNREAD;
2563 case SMS_STATUS_SENT:
2567 case SMS_STATUS_UNSENT:
2568 stat = AT_STO_UNSENT;
2572 err("Invalid msgStatus");
2574 return TCORE_RETURN_EINVAL;
2577 if ((saveMsg->msgDataPackage.msgLength > 0)
2578 && (saveMsg->msgDataPackage.msgLength <= SMS_SMDATA_SIZE_MAX))
2580 ScLength = (int)saveMsg->msgDataPackage.sca[0];
2584 dbg("ScLength is zero");
2590 dbg("Specifying SCA is currently not supported");
2596 util_byte_to_hex((const char *)saveMsg->msgDataPackage.tpduData, (char *)&(buf[pdu_len]), saveMsg->msgDataPackage.msgLength);
2598 pdu_len = pdu_len + 2*saveMsg->msgDataPackage.msgLength;
2600 buf[pdu_len] = '\0'; //Ensure termination
2602 dbg("pdu_len: [%d]", pdu_len);
2603 util_hex_dump(" ", sizeof(buf), (void *)buf);
2605 //AT+CMGW=<length>[,<stat>]<CR>PDU is given<ctrl-Z/ESC>
2606 cmd_str = g_strdup_printf("AT+CMGW=%d,%d%s%s\x1A", saveMsg->msgDataPackage.msgLength, stat, "\r", buf);
2607 pending = tcore_pending_new(obj, 0);
2608 atreq = tcore_at_request_new((const char *)cmd_str, "+CMGW", TCORE_AT_SINGLELINE);
2610 if(NULL == cmd_str || NULL == atreq || NULL == pending)
2612 err("Out of memory. Unable to proceed");
2613 dbg("cmd_str: [%p], atreq: [%p], pending: [%p]", cmd_str, atreq, pending);
2615 //free memory we own
2617 util_sms_free_memory(atreq);
2618 util_sms_free_memory(pending);
2621 return TCORE_RETURN_ENOMEM;
2624 util_hex_dump(" ", strlen(cmd_str), (void *)cmd_str);
2626 tcore_pending_set_request_data(pending, 0, atreq);
2627 tcore_pending_set_response_callback(pending, on_response_sms_save_msg, NULL);
2628 tcore_pending_link_user_request(pending, ur);
2629 tcore_pending_set_send_callback(pending, on_confirmation_sms_message_send, NULL);
2630 tcore_hal_send_request(hal, pending);
2635 return TCORE_RETURN_SUCCESS;
2638 err("Invalid Data len");
2640 return TCORE_RETURN_SMS_INVALID_DATA_LEN;
2643 static TReturn delete_msg(CoreObject *obj, UserRequest *ur)
2645 gchar *cmd_str = NULL;
2646 TcoreHal *hal = NULL;
2647 TcoreATRequest *atreq = NULL;
2648 TcorePending *pending = NULL;
2649 const struct treq_sms_delete_msg *deleteMsg = NULL;
2653 deleteMsg = tcore_user_request_ref_data(ur, NULL);
2654 hal = tcore_object_get_hal(obj);
2655 if(NULL == deleteMsg || NULL == hal)
2657 err("NULL input. Unable to proceed");
2658 dbg("deleteMsg: [%p], hal: [%p]", deleteMsg, hal);
2661 return TCORE_RETURN_EINVAL;
2664 dbg("index: %d", deleteMsg->index);
2666 cmd_str =g_strdup_printf("AT+CMGD=%d,0", deleteMsg->index+1);
2667 pending = tcore_pending_new(obj, 0);
2668 atreq = tcore_at_request_new((const char *)cmd_str, NULL, TCORE_AT_NO_RESULT);
2669 if(NULL == cmd_str || NULL == atreq || NULL == pending)
2671 err("Out of memory. Unable to proceed");
2672 dbg("cmd_str: [%p], atreq: [%p], pending: [%p]", cmd_str, atreq, pending);
2674 //free memory we own
2676 util_sms_free_memory(atreq);
2677 util_sms_free_memory(pending);
2680 return TCORE_RETURN_ENOMEM;
2683 util_hex_dump(" ", strlen(cmd_str), (void *)cmd_str);
2685 tcore_pending_set_request_data(pending, 0, atreq);
2686 tcore_pending_set_response_callback(pending, on_response_sms_delete_msg, (void *)(uintptr_t)(deleteMsg->index)); //storing index as user data for response
2687 tcore_pending_link_user_request(pending, ur);
2688 tcore_pending_set_send_callback(pending, on_confirmation_sms_message_send, NULL);
2689 tcore_hal_send_request(hal, pending);
2694 return TCORE_RETURN_SUCCESS;
2697 static TReturn get_storedMsgCnt(CoreObject *obj, UserRequest *ur)
2699 gchar *cmd_str = NULL;
2700 TcoreHal *hal = NULL;
2701 TcoreATRequest *atreq = NULL;
2702 TcorePending *pending = NULL;
2706 hal = tcore_object_get_hal(obj);
2709 err("NULL HAL. Unable to proceed");
2712 return TCORE_RETURN_EINVAL;
2715 cmd_str = g_strdup_printf("AT+CPMS=\"SM\"");
2716 pending = tcore_pending_new(obj, 0);
2717 atreq = tcore_at_request_new((const char *)cmd_str, "+CPMS", TCORE_AT_SINGLELINE);
2719 if(NULL == cmd_str || NULL == atreq || NULL == pending)
2721 err("Out of memory. Unable to proceed");
2722 dbg("cmd_str: [%p], atreq: [%p], pending: [%p]", cmd_str, atreq, pending);
2724 //free memory we own
2726 util_sms_free_memory(atreq);
2727 util_sms_free_memory(pending);
2730 return TCORE_RETURN_ENOMEM;
2733 util_hex_dump(" ", strlen(cmd_str), (void *)cmd_str);
2735 tcore_pending_set_request_data(pending, 0, atreq);
2736 tcore_pending_set_response_callback(pending, on_response_get_stored_msg_cnt, NULL);
2737 tcore_pending_link_user_request(pending, ur);
2738 tcore_pending_set_send_callback(pending, on_confirmation_sms_message_send, NULL);
2739 tcore_hal_send_request(hal, pending);
2744 return TCORE_RETURN_SUCCESS;
2747 static TReturn get_sca(CoreObject *obj, UserRequest *ur)
2749 gchar * cmd_str = NULL;
2750 TcoreHal *hal = NULL;
2751 TcoreATRequest *atreq = NULL;
2752 TcorePending *pending = NULL;
2756 hal = tcore_object_get_hal(obj);
2759 err("HAL NULL. Unable to proceed");
2762 return TCORE_RETURN_EINVAL;
2765 cmd_str = g_strdup_printf("AT+CSCA?");
2766 pending = tcore_pending_new(obj, 0);
2767 atreq = tcore_at_request_new((const char *)cmd_str, "+CSCA", TCORE_AT_SINGLELINE);
2769 if(NULL == cmd_str || NULL == atreq || NULL == pending)
2771 err("Out of memory. Unable to proceed");
2772 dbg("cmd_str: [%p], atreq: [%p], pending: [%p]", cmd_str, atreq, pending);
2774 //free memory we own
2776 util_sms_free_memory(atreq);
2777 util_sms_free_memory(pending);
2780 return TCORE_RETURN_ENOMEM;
2783 util_hex_dump(" ", strlen(cmd_str), (void *)cmd_str);
2785 tcore_pending_set_request_data(pending, 0, atreq);
2786 tcore_pending_set_response_callback(pending, on_response_get_sca, NULL);
2787 tcore_pending_link_user_request(pending, ur);
2788 tcore_pending_set_send_callback(pending, on_confirmation_sms_message_send, NULL);
2789 tcore_hal_send_request(hal, pending);
2794 return TCORE_RETURN_SUCCESS;
2797 static TReturn set_sca(CoreObject *obj, UserRequest *ur)
2799 gchar *cmd_str = NULL;
2800 TcoreHal *hal = NULL;
2801 TcoreATRequest *atreq = NULL;
2802 TcorePending *pending = NULL;
2803 const struct treq_sms_set_sca *setSca = NULL;
2808 setSca = tcore_user_request_ref_data(ur, NULL);
2809 hal = tcore_object_get_hal(obj);
2810 if(NULL == setSca || NULL == hal)
2812 err("NULL input. Unable to proceed");
2813 dbg("setSca: [%p], hal: [%p]", setSca, hal);
2816 return TCORE_RETURN_EINVAL;
2819 dbg("dialNumLen: %u, typeOfNum: %d, numPlanId: %d, ", setSca->scaInfo.dialNumLen, setSca->scaInfo.typeOfNum, setSca->scaInfo.numPlanId);
2821 util_hex_dump(" ", (SMS_SMSP_ADDRESS_LEN+1), (void *)setSca->scaInfo.diallingNum);
2823 addrType = ((setSca->scaInfo.typeOfNum << 4) | setSca->scaInfo.numPlanId) | 0x80;
2825 cmd_str = g_strdup_printf("AT+CSCA=\"%s\",%d", setSca->scaInfo.diallingNum, addrType);
2826 pending = tcore_pending_new(obj, 0);
2827 atreq = tcore_at_request_new((const char *)cmd_str, NULL, TCORE_AT_NO_RESULT);
2829 if(NULL == cmd_str || NULL == atreq || NULL == pending)
2831 err("Out of memory. Unable to proceed");
2832 dbg("cmd_str: [%p], atreq: [%p], pending: [%p]", cmd_str, atreq, pending);
2834 //free memory we own
2836 util_sms_free_memory(atreq);
2837 util_sms_free_memory(pending);
2840 return TCORE_RETURN_ENOMEM;
2843 util_hex_dump(" ", strlen(cmd_str), (void *)cmd_str);
2845 tcore_pending_set_request_data(pending, 0, atreq);
2846 tcore_pending_set_response_callback(pending, on_response_set_sca, NULL);
2847 tcore_pending_link_user_request(pending, ur);
2848 tcore_pending_set_send_callback(pending, on_confirmation_sms_message_send, NULL);
2849 tcore_hal_send_request(hal, pending);
2854 return TCORE_RETURN_SUCCESS;
2857 static TReturn get_cb_config(CoreObject *obj, UserRequest *ur)
2859 gchar *cmd_str = NULL;
2860 TcoreHal *hal = NULL;
2861 TcoreATRequest *atreq = NULL;
2862 TcorePending *pending = NULL;
2866 hal = tcore_object_get_hal(obj);
2869 err("NULL HAL. Unable to proceed");
2872 return TCORE_RETURN_EINVAL;
2875 cmd_str = g_strdup_printf("AT+CSCB?");
2876 pending = tcore_pending_new(obj, 0);
2877 atreq = tcore_at_request_new((const char *)cmd_str, "+CSCB", TCORE_AT_SINGLELINE);
2878 if(NULL == cmd_str || NULL == atreq || NULL == pending)
2880 err("Out of memory. Unable to proceed");
2881 dbg("cmd_str: [%p], atreq: [%p], pending: [%p]", cmd_str, atreq, pending);
2883 //free memory we own
2885 util_sms_free_memory(atreq);
2886 util_sms_free_memory(pending);
2889 return TCORE_RETURN_ENOMEM;
2892 util_hex_dump(" ", strlen(cmd_str), (void *)cmd_str);
2894 tcore_pending_set_request_data(pending, 0, atreq);
2895 tcore_pending_set_response_callback(pending, on_response_get_cb_config, NULL);
2896 tcore_pending_set_send_callback(pending, on_confirmation_sms_message_send, NULL);
2897 tcore_pending_link_user_request(pending, ur);
2898 tcore_hal_send_request(hal, pending);
2903 return TCORE_RETURN_SUCCESS;
2906 static TReturn set_cb_config(CoreObject *obj, UserRequest *ur)
2908 gchar *cmd_str = NULL;
2909 gchar *mids_str = NULL;
2910 GString *mids_GString = NULL;
2912 TcoreHal *hal = NULL;
2913 TcoreATRequest *atreq = NULL;
2914 TcorePending *pending = NULL;
2915 const struct treq_sms_set_cb_config *setCbConfig = NULL;
2920 setCbConfig = tcore_user_request_ref_data(ur, NULL);
2921 hal = tcore_object_get_hal(obj);
2922 if(NULL == setCbConfig || NULL == hal)
2924 err("NULL input. Unable to proceed");
2925 dbg("setCbConfig: [%p], hal: [%p]", setCbConfig, hal);
2928 return TCORE_RETURN_EINVAL;
2931 dbg("bCBEnabled: %d, selectedId: %x, msgIdMaxCount: %x, msgIdCount: %d", setCbConfig->bCBEnabled, setCbConfig->selectedId, setCbConfig->msgIdMaxCount, setCbConfig->msgIdCount);
2932 util_hex_dump(" ", SMS_GSM_SMS_CBMI_LIST_SIZE_MAX, (void *)setCbConfig->msgIDs);
2934 if (setCbConfig->bCBEnabled == FALSE) //AT+CSCB=0: Disable CBS
2936 cmd_str = g_strdup_printf("AT+CSCB=0");
2940 if(setCbConfig->selectedId == SMS_CBMI_SELECTED_SOME) //AT+CSCB=0,<mids>,<dcss>: Enable CBS for specified <mids> and <dcss>
2942 dbg("Enabling specified CBMIs");
2943 mids_GString = g_string_new(g_strdup_printf("%d", setCbConfig->msgIDs[0]));
2945 for(loop_ctr=1; loop_ctr <setCbConfig->msgIdCount; loop_ctr++)
2947 mids_GString = g_string_append(mids_GString, ",");
2948 mids_GString = g_string_append(mids_GString, g_strdup_printf("%d", setCbConfig->msgIDs[loop_ctr]));
2951 mids_str = g_string_free(mids_GString, FALSE);
2952 cmd_str = g_strdup_printf("AT+CSCB=0,\"%s\"", mids_str);
2956 else if (setCbConfig->selectedId == SMS_CBMI_SELECTED_ALL) //AT+CSCB=1: Enable CBS for all <mids> and <dcss>
2958 dbg("Enabling all CBMIs");
2959 cmd_str = g_strdup_printf("AT+CSCB=1");
2963 pending = tcore_pending_new(obj, 0);
2964 atreq = tcore_at_request_new((const char *)cmd_str, NULL, TCORE_AT_NO_RESULT);
2965 if(NULL == cmd_str || NULL == atreq || NULL == pending)
2967 err("Out of memory. Unable to proceed");
2968 dbg("cmd_str: [%p], atreq: [%p], pending: [%p]", cmd_str, atreq, pending);
2970 //free memory we own
2972 util_sms_free_memory(atreq);
2973 util_sms_free_memory(pending);
2976 return TCORE_RETURN_ENOMEM;
2979 util_hex_dump(" ", strlen(cmd_str), (void *)cmd_str);
2981 tcore_pending_set_request_data(pending, 0, atreq);
2982 tcore_pending_set_response_callback(pending, on_response_set_cb_config, NULL);
2983 tcore_pending_link_user_request(pending, ur);
2984 tcore_pending_set_send_callback(pending, on_confirmation_sms_message_send, NULL);
2985 tcore_hal_send_request(hal, pending);
2990 return TCORE_RETURN_SUCCESS;
2993 static TReturn set_mem_status(CoreObject *obj, UserRequest *ur)
2995 gchar *cmd_str = NULL;
2996 TcoreHal *hal = NULL;
2997 TcoreATRequest *atreq = NULL;
2998 TcorePending *pending = NULL;
2999 const struct treq_sms_set_mem_status *setMemStatus = NULL;
3000 int memoryStatus = 0;
3004 setMemStatus = tcore_user_request_ref_data(ur, NULL);
3005 hal = tcore_object_get_hal(obj);
3006 if(NULL == setMemStatus || NULL == hal)
3008 err("NULL input. Unable to proceed");
3009 dbg("setMemStatus: [%p], hal: [%p]", setMemStatus, hal);
3012 return TCORE_RETURN_EINVAL;
3015 dbg("memory_status: %d", setMemStatus->memory_status);
3017 if(setMemStatus->memory_status < SMS_PDA_MEMORY_STATUS_AVAILABLE
3018 || setMemStatus->memory_status > SMS_PDA_MEMORY_STATUS_FULL)
3020 err("Invalid memory_status");
3023 return TCORE_RETURN_EINVAL;
3026 switch (setMemStatus->memory_status)
3028 case SMS_PDA_MEMORY_STATUS_AVAILABLE:
3029 memoryStatus = AT_MEMORY_AVAILABLE;
3032 case SMS_PDA_MEMORY_STATUS_FULL:
3033 memoryStatus = AT_MEMORY_FULL;
3037 err("Invalid memory_status");
3039 return TCORE_RETURN_EINVAL;
3042 cmd_str = g_strdup_printf("AT+XTESM=%d", memoryStatus);
3043 pending = tcore_pending_new(obj, 0);
3044 atreq = tcore_at_request_new((const char *)cmd_str, NULL, TCORE_AT_NO_RESULT);
3046 if(NULL == cmd_str || NULL == atreq || NULL == pending)
3048 err("Out of memory. Unable to proceed");
3049 dbg("cmd_str: [%p], atreq: [%p], pending: [%p]", cmd_str, atreq, pending);
3051 //free memory we own
3053 util_sms_free_memory(atreq);
3054 util_sms_free_memory(pending);
3057 return TCORE_RETURN_ENOMEM;
3060 util_hex_dump(" ", strlen(cmd_str), (void *)cmd_str);
3062 tcore_pending_set_request_data(pending, 0, atreq);
3063 tcore_pending_set_response_callback(pending, on_response_set_mem_status, NULL);
3064 tcore_pending_link_user_request(pending, ur);
3065 tcore_pending_set_send_callback(pending, on_confirmation_sms_message_send, NULL);
3066 tcore_hal_send_request(hal, pending);
3071 return TCORE_RETURN_SUCCESS;
3074 static TReturn set_delivery_report(CoreObject *obj, UserRequest *ur)
3076 struct tresp_sms_set_delivery_report respSetDeliveryReport = {0,};
3078 respSetDeliveryReport.result = SMS_SUCCESS;
3082 dbg("CP takes care of sending SMS ack to network for all classes of SMS. Sending default success.");
3084 tcore_user_request_send_response(ur, TRESP_SMS_SET_DELIVERY_REPORT, sizeof(struct tresp_sms_set_delivery_report), &respSetDeliveryReport);
3087 return TCORE_RETURN_SUCCESS;
3090 static TReturn set_msg_status(CoreObject *obj, UserRequest *ur)
3092 gchar *cmd_str = NULL;
3093 TcoreHal *hal = NULL;
3094 TcoreATRequest *atreq = NULL;
3095 TcorePending *pending = NULL;
3096 const struct treq_sms_set_msg_status *msg_status = NULL;
3100 msg_status = tcore_user_request_ref_data(ur, NULL);
3102 cmd_str = g_strdup_printf("AT+CRSM=178,28476,%d,4,%d", (msg_status->index+1), AT_EF_SMS_RECORD_LEN);
3103 atreq = tcore_at_request_new((const char *)cmd_str, "+CRSM", TCORE_AT_SINGLELINE);
3104 pending = tcore_pending_new(obj, 0);
3105 if(NULL == cmd_str || NULL == atreq || NULL == pending)
3107 err("Out of memory. Unable to proceed");
3108 dbg("cmd_str: [%p], atreq: [%p], pending: [%p]", cmd_str, atreq, pending);
3110 //free memory we own
3112 util_sms_free_memory(atreq);
3113 util_sms_free_memory(pending);
3116 return TCORE_RETURN_ENOMEM;
3119 util_hex_dump(" ", strlen(cmd_str), (void *)cmd_str);
3121 tcore_pending_set_request_data(pending, 0, atreq);
3122 tcore_pending_set_response_callback(pending, _response_get_efsms_data, NULL);
3123 tcore_pending_link_user_request(pending, ur);
3124 tcore_pending_set_send_callback(pending, on_confirmation_sms_message_send, NULL);
3125 tcore_hal_send_request(hal, pending);
3130 return TCORE_RETURN_SUCCESS;
3133 static TReturn get_sms_params(CoreObject *obj, UserRequest *ur)
3135 gchar *cmd_str = NULL;
3136 TcoreHal *hal = NULL;
3137 TcoreATRequest *atreq = NULL;
3138 TcorePending *pending = NULL;
3139 const struct treq_sms_get_params *getSmsParams = NULL;
3140 int record_len = 0 , *smsp_record_len = NULL;
3144 getSmsParams = tcore_user_request_ref_data(ur, NULL);
3145 hal = tcore_object_get_hal(obj);
3146 if(NULL == getSmsParams || NULL == hal)
3148 err("NULL input. Unable to proceed");
3149 dbg("getSmsParams: [%p], hal: [%p]", getSmsParams, hal);
3152 return TCORE_RETURN_EINVAL;
3155 smsp_record_len = tcore_plugin_ref_property(tcore_object_ref_plugin(obj), "SMSPRECORDLEN");
3156 record_len = *smsp_record_len;
3157 dbg("record len from property %d", record_len);
3159 //AT+CRSM=command>[,<fileid>[,<P1>,<P2>,<P3>[,<data>[,<pathid>]]]]
3160 cmd_str = g_strdup_printf("AT+CRSM=178,28482,%d,4,%d", (getSmsParams->index + 1), record_len);
3162 dbg("cmd_str is %s",cmd_str);
3164 atreq = tcore_at_request_new((const char *)cmd_str, "+CRSM", TCORE_AT_SINGLELINE);
3165 pending = tcore_pending_new(obj, 0);
3166 if(NULL == cmd_str || NULL == atreq || NULL == pending)
3168 err("Out of memory. Unable to proceed");
3169 dbg("cmd_str: [%p], atreq: [%p], pending: [%p]", cmd_str, atreq, pending);
3171 //free memory we own
3173 util_sms_free_memory(atreq);
3174 util_sms_free_memory(pending);
3177 return TCORE_RETURN_ENOMEM;
3180 util_hex_dump(" ", strlen(cmd_str), (void *)cmd_str);
3182 tcore_pending_set_request_data(pending, 0, atreq);
3183 tcore_pending_set_response_callback(pending, on_response_get_sms_params, NULL);
3184 tcore_pending_link_user_request(pending, ur);
3185 tcore_pending_set_send_callback(pending, on_confirmation_sms_message_send, NULL);
3186 tcore_hal_send_request(hal, pending);
3191 return TCORE_RETURN_SUCCESS;
3194 static TReturn set_sms_params(CoreObject *obj, UserRequest *ur)
3196 gchar *cmd_str = NULL;
3197 char *encoded_data = NULL;
3198 unsigned char *temp_data = NULL;
3199 int SMSPRecordLen = 0;
3201 TcoreHal *hal = NULL;
3202 TcoreATRequest *atreq = NULL;
3203 TcorePending *pending = NULL;
3204 const struct treq_sms_set_params *setSmsParams = NULL;
3205 int encoded_data_len = 0;
3209 setSmsParams = tcore_user_request_ref_data(ur, NULL);
3210 hal = tcore_object_get_hal(obj);
3211 if(NULL == setSmsParams || NULL == hal)
3213 err("NULL input. Unable to proceed");
3214 dbg("setSmsParams: [%p], hal: [%p]", setSmsParams, hal);
3219 //EFsmsp file size is 28 +Y bytes (Y is alpha id size)
3220 SMSPRecordLen = 28 + setSmsParams->params.alphaIdLen;
3221 temp_data = calloc(SMSPRecordLen,1);
3222 encoded_data = calloc(SMSPRecordLen*2 + 1,1);
3224 _tcore_util_sms_encode_smsParameters(&(setSmsParams->params), temp_data, SMSPRecordLen);
3226 util_byte_to_hex((const char *)temp_data, (char *)encoded_data,SMSPRecordLen);
3228 encoded_data_len = ((SMSPRecordLen) * 2);
3230 hal = tcore_object_get_hal(obj);
3231 pending = tcore_pending_new(obj, 0);
3233 dbg("alpha id len %d encoded data %s. Encoded data len %d",setSmsParams->params.alphaIdLen,encoded_data, encoded_data_len);
3234 cmd_str = g_strdup_printf("AT+CRSM=220,28482,%d,4,%d,\"%s\"",(setSmsParams->params.recordIndex+1),SMSPRecordLen,encoded_data);
3236 dbg("cmd str is %s",cmd_str);
3237 atreq = tcore_at_request_new(cmd_str, "+CRSM:", TCORE_AT_SINGLELINE);
3239 if(NULL == cmd_str || NULL == atreq || NULL == pending)
3241 err("Out of memory. Unable to proceed");
3242 dbg("cmd_str: [%p], atreq: [%p], pending: [%p]", cmd_str, atreq, pending);
3244 //free memory we own
3246 util_sms_free_memory(atreq);
3247 util_sms_free_memory(pending);
3249 util_sms_free_memory(temp_data);
3250 util_sms_free_memory(encoded_data);
3253 return TCORE_RETURN_ENOMEM;
3256 util_hex_dump(" ", strlen(cmd_str), (void *)cmd_str);
3258 tcore_pending_set_request_data(pending, 0,atreq);
3259 tcore_pending_set_response_callback(pending, on_response_set_sms_params, NULL);
3260 tcore_pending_link_user_request(pending, ur);
3261 tcore_pending_set_send_callback(pending, on_confirmation_sms_message_send, NULL);
3262 tcore_hal_send_request(hal, pending);
3265 util_sms_free_memory(temp_data);
3266 util_sms_free_memory(encoded_data);
3271 static TReturn get_paramcnt(CoreObject *obj, UserRequest *ur)
3273 gchar *cmd_str = NULL;
3274 TcoreHal *hal = NULL;
3275 TcoreATRequest *atreq = NULL;
3276 TcorePending *pending = NULL;
3280 hal = tcore_object_get_hal(obj);
3283 err("NULL HAL. Unable to proceed");
3286 return TCORE_RETURN_EINVAL;
3289 //AT+CRSM=command>[,<fileid>[,<P1>,<P2>,<P3>[,<data>[,<pathid>]]]]
3290 cmd_str = g_strdup_printf("AT+CRSM=192,28482");
3291 atreq = tcore_at_request_new((const char *)cmd_str, "+CRSM", TCORE_AT_SINGLELINE);
3292 pending = tcore_pending_new(obj, 0);
3294 if (NULL == cmd_str || NULL == atreq || NULL == pending)
3296 err("NULL pointer. Unable to proceed");
3297 dbg("cmd_str: [%p], atreq: [%p], pending: [%p]", cmd_str, atreq, pending);
3299 //free memory we own
3301 util_sms_free_memory(atreq);
3302 util_sms_free_memory(pending);
3305 return TCORE_RETURN_FAILURE;
3308 util_hex_dump(" ", strlen(cmd_str), (void *)cmd_str);
3310 tcore_pending_set_request_data(pending, 0, atreq);
3311 tcore_pending_set_response_callback(pending, on_response_get_paramcnt, NULL);
3312 tcore_pending_link_user_request(pending, ur);
3313 tcore_pending_set_send_callback(pending, on_confirmation_sms_message_send, NULL);
3314 tcore_hal_send_request(hal, pending);
3319 return TCORE_RETURN_SUCCESS;
3322 static struct tcore_sms_operations sms_ops =
3324 .send_umts_msg = send_umts_msg,
3325 .read_msg = read_msg,
3326 .save_msg = save_msg,
3327 .delete_msg = delete_msg,
3328 .get_storedMsgCnt = get_storedMsgCnt,
3331 .get_cb_config = get_cb_config,
3332 .set_cb_config = set_cb_config,
3333 .set_mem_status = set_mem_status,
3334 .get_pref_brearer = NULL,
3335 .set_pref_brearer = NULL,
3336 .set_delivery_report = set_delivery_report,
3337 .set_msg_status = set_msg_status,
3338 .get_sms_params = get_sms_params,
3339 .set_sms_params = set_sms_params,
3340 .get_paramcnt = get_paramcnt,
3343 gboolean s_sms_init(TcorePlugin *plugin, TcoreHal *hal)
3345 CoreObject *obj = NULL;
3346 struct property_sms_info *data = NULL;
3347 GQueue *work_queue = NULL;
3348 int *smsp_record_len = NULL;
3351 dbg("plugin: [%p]", plugin);
3352 dbg("hal: [%p]", hal);
3354 obj = tcore_sms_new(plugin, "umts_sms", &sms_ops, hal);
3356 data = calloc(sizeof(struct property_sms_info), 1);
3358 if (NULL == obj || NULL == data)
3360 err("Unable to initialize. Exiting");
3367 work_queue = g_queue_new();
3368 tcore_object_link_user_data(obj, work_queue);
3370 //Registering for SMS notifications
3371 tcore_object_add_callback(obj, "\e+CMTI", on_event_class2_sms_incom_msg, NULL);
3372 tcore_object_add_callback(obj, "\e+CMT", on_event_sms_incom_msg, NULL);
3374 tcore_object_add_callback(obj, "\e+CDS", on_event_sms_incom_msg, NULL);
3375 tcore_object_add_callback(obj, "+XSMSMMSTAT", on_event_sms_memory_status, NULL);
3376 tcore_object_add_callback(obj, "+CMS", on_event_sms_memory_status, NULL);
3378 tcore_object_add_callback(obj, "\e+CBMI", on_event_sms_cb_incom_msg, NULL);
3379 tcore_object_add_callback(obj, "\e+CBM", on_event_sms_cb_incom_msg, NULL);
3380 tcore_object_add_callback(obj, "+XSIM", on_event_sms_ready_status, NULL);
3382 tcore_plugin_link_property(plugin, "SMS", data);
3384 //storing smsp record length
3385 smsp_record_len = calloc(sizeof(int), 1);
3386 tcore_plugin_link_property(plugin, "SMSPRECORDLEN", smsp_record_len);
3392 void s_sms_exit(TcorePlugin *plugin)
3394 CoreObject *obj = NULL;
3395 struct property_sms_info *data = NULL;
3398 dbg("plugin: [%p]", plugin);
3400 obj = tcore_plugin_ref_core_object(plugin, "umts_sms");
3403 err("NULL core object. Nothing to do.");
3406 tcore_sms_free(obj);
3408 data = tcore_plugin_ref_property(plugin, "SMS");
3409 util_sms_free_memory(data);