4 * Copyright (c) 2012 Samsung Electronics Co., Ltd. All rights reserved.
\r
6 * Contact: Harish Bishnoi <hbishnoi@samsung.com>
8 * Licensed under the Apache License, Version 2.0 (the "License");
\r
9 * you may not use this file except in compliance with the License.
\r
10 * You may obtain a copy of the License at
\r
12 * http://www.apache.org/licenses/LICENSE-2.0
\r
14 * Unless required by applicable law or agreed to in writing, software
\r
15 * distributed under the License is distributed on an "AS IS" BASIS,
\r
16 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
\r
17 * See the License for the specific language governing permissions and
\r
18 * limitations under the License.
\r
30 #include <core_object.h>
\r
33 #include <co_modem.h>
\r
34 #include <storage.h>
\r
39 #include "s_common.h"
\r
40 #include "s_modem.h"
\r
43 #define ID_RESERVED_AT 0x0229
\r
45 #define MAX_VERSION_LEN 32
\r
46 #define TAPI_MISC_ME_SN_LEN_MAX 32
\r
47 #define TAPI_MISC_PRODUCT_CODE_LEN_MAX 32
\r
48 #define TAPI_MISC_MODEL_ID_LEN_MAX 17
\r
49 #define TAPI_MISC_PRL_ERI_VER_LEN_MAX 17
\r
51 #define CPAS_RES_READY 0
\r
52 #define CPAS_RES_UNAVAIL 1
\r
53 #define CPAS_RES_UNKNOWN 2
\r
54 #define CPAS_RES_RINGING 3
\r
55 #define CPAS_RES_CALL_PROGRESS 4
\r
56 #define CPAS_RES_ASLEEP 5
\r
57 #define AT_VER_LEN 20
\r
62 CP_STATE_CRASH_RESET,
\r
63 CP_STATE_CRASH_EXIT,
\r
66 CP_STATE_NV_REBUILDING,
\r
67 CP_STATE_LOADER_DONE,
\r
71 TAPI_MISC_ME_IMEI = 0x00, /**< 0x00: IMEI, GSM/UMTS device */
\r
72 TAPI_MISC_ME_ESN = 0x01, /**< 0x01: ESN(Electronic Serial Number), It`s essentially run out. CDMA device */
\r
73 TAPI_MISC_ME_MEID = 0x02, /**< 0x02: MEID, This value can have hexa decimal digits. CDMA device */
\r
74 TAPI_MISC_ME_MAX = 0xff /**< 0xff: reserved */
\r
75 } TelMiscSNIndexType_t;
\r
78 TelMiscSNIndexType_t sn_index; /**< serial number index */
\r
79 int sn_len; /**< Length */
\r
80 unsigned char szNumber[TAPI_MISC_ME_SN_LEN_MAX]; /**< Number */
\r
81 } TelMiscSNInformation;
\r
84 * Mobile Equipment Version Information
\r
87 unsigned char ver_mask; /**< version mask - 0x01:SW_ver, 0x02:HW_ver, 0x04:RF_CAL_date, 0x08:Product_code, 0x10:Model_ID, 0x20:PRL, 0x04:ERI, 0xff:all */
\r
88 unsigned char szSwVersion[MAX_VERSION_LEN]; /**< Software version, null termination */
\r
89 unsigned char szHwVersion[MAX_VERSION_LEN]; /**< Hardware version, null termination */
\r
90 unsigned char szRfCalDate[MAX_VERSION_LEN]; /**< Calculation Date, null termination */
\r
91 unsigned char szProductCode[TAPI_MISC_PRODUCT_CODE_LEN_MAX]; /**< product code, null termination */
\r
92 unsigned char szModelId[TAPI_MISC_MODEL_ID_LEN_MAX]; /**< model id (only for CDMA), null termination */
\r
93 unsigned char prl_nam_num; /**< number of PRL NAM fields */
\r
94 unsigned char szPrlVersion[TAPI_MISC_PRL_ERI_VER_LEN_MAX * 3];/**< prl version (only for CDMA), null termination */
\r
95 unsigned char eri_nam_num; /**< number of PRL NAM fields */
\r
96 unsigned char szEriVersion[TAPI_MISC_PRL_ERI_VER_LEN_MAX * 3];/**< eri version (only for CDMA), null termination */
\r
97 } TelMiscVersionInformation;
\r
100 void prepare_and_send_pending_request(TcorePlugin *plugin, char *co_name, const char *at_cmd, const char* prefix, enum tcore_at_command_type at_cmd_type, TcorePendingResponseCallback callback);
\r
101 static void on_confirmation_modem_message_send(TcorePending *p, gboolean result, void *user_data); // from Kernel
\r
102 void on_response_bootup_subscription(TcorePending *p, int data_len, const void *data, void *user_data);
\r
103 void on_response_last_bootup_subscription(TcorePending *p, int data_len, const void *data, void *user_data);
\r
104 static void on_timeout_modem_poweron(TcorePending *p, void *user_data);
\r
105 static void on_response_enable_proactive_command(TcorePending *p, int data_len, const void *data, void *user_data);
\r
107 static void on_timeout_modem_poweron(TcorePending *p, void *user_data)
\r
109 unsigned int data_len = 0;
\r
110 char data[] = "AT+CPAS";
\r
111 dbg("TIMEOUT for 1st AT Command !!!!! NO Response for initial AT command. Resending it");
\r
112 data_len = sizeof(data);
\r
114 /* Retransmit 1st AT command directly via HAL, don't disturb pending queue. */
\r
115 /* HAL was passed as user_data, re-use it */
\r
118 tcore_hal_send_data(user_data, data_len, (void *)data);
\r
122 static void on_confirmation_modem_message_send(TcorePending *p, gboolean result, void *user_data)
\r
124 dbg("on_confirmation_modem_message_send - msg out from queue.\n");
\r
126 if (result == FALSE) {
\r
135 static void on_response_enable_proactive_command(TcorePending *p, int data_len, const void *data, void *user_data)
\r
137 const TcoreATResponse *resp = data;
\r
139 if(resp->success > 0){
\r
140 dbg("RESPONSE OK proactive command enabled");
\r
144 dbg("RESPONSE NOK proactive command disabled");
\r
148 void prepare_and_send_pending_request(TcorePlugin *plugin, char *co_name, const char *at_cmd, const char* prefix, enum tcore_at_command_type at_cmd_type, TcorePendingResponseCallback callback)
\r
150 TcoreATRequest *req = NULL;
\r
151 TcoreHal *hal = NULL;
\r
152 CoreObject *o= NULL;
\r
153 TcorePending *pending = NULL;
\r
156 o = tcore_plugin_ref_core_object(plugin, co_name);
\r
157 hal = tcore_object_get_hal(o);
\r
158 dbg("hal: %p", hal);
\r
160 pending = tcore_pending_new(o, 0);
\r
162 dbg("Pending is NULL");
\r
163 req = tcore_at_request_new(at_cmd, prefix, at_cmd_type);
\r
165 dbg("cmd : %s, prefix(if any) :%s, cmd_len : %d", req->cmd, req->prefix, strlen(req->cmd));
\r
167 tcore_pending_set_request_data(pending, 0, req);
\r
168 tcore_pending_set_response_callback(pending, callback, NULL);
\r
169 tcore_pending_set_send_callback(pending, on_confirmation_modem_message_send, NULL);
\r
170 tcore_pending_link_user_request(pending, NULL); //set user request to NULL - this is intenal request
\r
171 ret = tcore_hal_send_request(hal, pending);
\r
175 void on_response_bootup_subscription(TcorePending *p, int data_len, const void *data, void *user_data)
\r
177 const TcoreATResponse *resp = data;
\r
178 dbg("enry of on_response_bootup_subscription() - response comes\n");
\r
184 dbg("result ERROR");
\r
188 void on_response_last_bootup_subscription(TcorePending *p, int data_len, const void *data, void *user_data)
\r
190 const TcoreATResponse *resp = data;
\r
191 dbg("enry of on_response_last_bootup_subscription() - final response comes\n");
\r
198 dbg("Response for AT+CLIP. Boot-up configration completed for IMC modem. Bring CP to online based on Flightmode status\n");
\r
199 on_event_modem_power(NULL, NULL, tcore_pending_ref_plugin(p));
\r
202 static void on_response_power_off(TcorePending *p, int data_len, const void *data, void *user_data)
\r
206 o = tcore_pending_ref_core_object(p);
\r
207 h = tcore_object_get_hal(o);
\r
209 dbg("modem power off");
\r
211 tcore_hal_set_power_state(h, FALSE);
\r
214 static void on_response_set_flight_mode(TcorePending *p, int data_len, const void *data, void *user_data)
\r
216 CoreObject *o = NULL;
217 UserRequest *ur = NULL;
\r
218 const TcoreATResponse *ATresp = data;
\r
219 GSList *tokens=NULL;
\r
220 const char *line = NULL;
\r
221 struct tresp_modem_set_flightmode res = {0};
\r
223 struct tnoti_modem_flight_mode modem_flight_mode = {0};
\r
224 const struct treq_modem_set_flightmode *req_data = NULL;
226 o = tcore_pending_ref_core_object(p);
\r
228 if(ATresp->success > 0){
\r
229 dbg("RESPONSE OK - flight mode operation finished");
\r
230 res.result = TCORE_RETURN_SUCCESS;
\r
233 dbg("RESPONSE NOK");
\r
234 line = (const char*)ATresp->final_response;
\r
235 tokens = tcore_at_tok_new(line);
\r
237 if (g_slist_length(tokens) < 1) {
\r
238 dbg("err cause not specified or string corrupted");
\r
239 res.result = TCORE_RETURN_3GPP_ERROR;
\r
242 response = atoi(g_slist_nth_data(tokens, 0));
\r
243 /* TODO: CMEE error mapping is required. */
\r
244 res.result = TCORE_RETURN_3GPP_ERROR;
\r
248 ur = tcore_pending_ref_user_request(p);
\r
250 dbg("No user request. Internal request created during boot-up sequence");
\r
252 if(ATresp->success > 0){
\r
253 modem_flight_mode.enable = tcore_modem_get_flight_mode_state(o);
\r
254 dbg("sucess case - Sending Flight Mode Notification (%d) to Telephony Server",modem_flight_mode.enable);
\r
256 tcore_server_send_notification(tcore_plugin_ref_server(tcore_object_ref_plugin(o)), o, TNOTI_MODEM_FLIGHT_MODE,
\r
257 sizeof(struct tnoti_modem_flight_mode), &modem_flight_mode);
\r
261 dbg("Sending response for Flight mode operation");
\r
262 tcore_user_request_send_response(ur, TRESP_MODEM_SET_FLIGHTMODE, sizeof(struct tresp_modem_set_flightmode), &res);
\r
264 req_data = tcore_user_request_ref_data(ur, NULL);
266 if (req_data->enable == 0) {
267 dbg("Flight mode is disabled, trigger COPS to register on network");
268 /* Trigger Network registration (for the moment automatic) */
269 prepare_and_send_pending_request(tcore_object_ref_plugin(o), "modem", "AT+COPS=0", NULL, TCORE_AT_NO_RESULT, NULL);
273 tcore_at_tok_free(tokens);
\r
276 static void on_response_imei(TcorePending *p, int data_len, const void *data, void *user_data)
\r
278 const TcoreATResponse* resp = data;
\r
279 TcorePlugin *plugin = NULL;
\r
280 struct tresp_modem_get_imei res;
\r
281 TelMiscSNInformation *imei_property = NULL;
\r
282 UserRequest* ur = NULL;
\r
283 GSList *tokens=NULL;
\r
287 memset(&res, 0, sizeof(struct tresp_modem_get_imei));
\r
289 if(resp->success > 0)
\r
291 dbg("RESPONSE OK");
\r
293 line = (const char*)resp->lines->data;
\r
294 tokens = tcore_at_tok_new(line);
\r
295 if (g_slist_length(tokens) != 1) {
\r
296 msg("invalid message");
\r
300 res.result = TCORE_RETURN_SUCCESS;
\r
301 strncpy(res.imei, g_slist_nth_data(tokens, 0), 16);
\r
303 dbg("imei = [%s]", res.imei);
\r
305 plugin = tcore_pending_ref_plugin(p);
\r
306 imei_property = tcore_plugin_ref_property(plugin, "IMEI");
\r
309 imei_property->sn_index = TAPI_MISC_ME_IMEI;
\r
310 imei_property->sn_len = strlen(res.imei);
\r
311 memcpy(imei_property->szNumber, res.imei, imei_property->sn_len);
\r
316 dbg("RESPONSE NOK");
\r
318 line = (const char*)resp->lines->data;
\r
319 tokens = tcore_at_tok_new(line);
\r
323 if (g_slist_length(tokens) < 1) {
\r
324 dbg("err cause not specified or string corrupted");
\r
325 res.result = TCORE_RETURN_3GPP_ERROR;
\r
329 response = atoi(g_slist_nth_data(tokens, 0));
\r
330 /* TODO: CMEE error mapping is required. */
\r
331 res.result = TCORE_RETURN_3GPP_ERROR;
\r
335 ur = tcore_pending_ref_user_request(p);
\r
336 tcore_user_request_send_response(ur, TRESP_MODEM_GET_IMEI, sizeof(struct tresp_modem_get_imei), &res);
\r
340 tcore_at_tok_free(tokens);
\r
345 static void on_response_version(TcorePending *p, int data_len, const void *data, void *user_data)
\r
347 const TcoreATResponse *resp = data;
\r
348 TcorePlugin *plugin = NULL;
\r
349 struct tresp_modem_get_version res = {0};
\r
350 TelMiscVersionInformation *vi_property = NULL;
\r
351 TelMiscVersionInformation *vi = NULL;
\r
352 UserRequest *ur = NULL;
\r
353 GSList* tokens = NULL;
\r
354 const char* line=NULL;
\r
357 char *caldate=NULL;
\r
363 if(resp->success > 0)
\r
365 dbg("RESPONSE OK");
\r
367 line = (const char*)resp->lines->data;
\r
368 tokens = tcore_at_tok_new(line);
\r
369 if (g_slist_length(tokens) != 5) {
\r
370 msg("invalid message");
\r
375 swver = g_slist_nth_data(tokens, 0);
\r
376 hwver = g_slist_nth_data(tokens, 1);
\r
377 caldate = g_slist_nth_data(tokens, 2);
\r
378 pcode = g_slist_nth_data(tokens, 3);
\r
379 id = g_slist_nth_data(tokens, 4);
\r
381 dbg("version: sw=[%s], hw=[%s], rf_cal=[%s], product_code=[%s], model_id=[%s]", swver, hwver, caldate, pcode, id);
\r
383 vi = calloc(sizeof(TelMiscVersionInformation), 1);
\r
385 memcpy(vi->szSwVersion, swver, strlen(swver));
\r
387 memcpy(vi->szHwVersion, hwver, strlen(hwver));
\r
389 memcpy(vi->szRfCalDate, caldate, strlen(caldate));
\r
391 memcpy(vi->szProductCode, pcode,strlen(pcode));
\r
393 memcpy(vi->szModelId, id, strlen(id));
\r
395 memset(&res, 0, sizeof(struct tresp_modem_get_version));
\r
398 snprintf(res.software, (AT_VER_LEN >strlen(swver) ?strlen(swver):AT_VER_LEN), "%s", swver);
\r
400 snprintf(res.hardware, (AT_VER_LEN >strlen(hwver) ?strlen(hwver):AT_VER_LEN), "%s", hwver);
\r
402 plugin = tcore_pending_ref_plugin(p);
\r
403 vi_property = tcore_plugin_ref_property(plugin, "VERSION");
\r
404 memcpy(vi_property, vi, sizeof(TelMiscVersionInformation));
\r
409 dbg("RESPONSE NOK");
\r
411 line = (const char*)resp->lines->data;
\r
412 tokens = tcore_at_tok_new(line);
\r
415 memset(&res, 0, sizeof(struct tresp_modem_get_version));
\r
418 if (g_slist_length(tokens) < 1) {
\r
419 dbg("err cause not specified or string corrupted");
\r
420 res.result = TCORE_RETURN_3GPP_ERROR;
\r
424 response = atoi(g_slist_nth_data(tokens, 0));
\r
425 /* TODO: CMEE error mapping is required. */
\r
426 res.result = TCORE_RETURN_3GPP_ERROR;
\r
430 ur = tcore_pending_ref_user_request(p);
\r
431 tcore_user_request_send_response(ur, TRESP_MODEM_GET_VERSION, sizeof(struct tresp_modem_get_version), &res);
\r
435 tcore_at_tok_free(tokens);
\r
440 static gboolean on_event_bootup_sim_status(CoreObject *o, const void *event_info, void *user_data)
\r
442 GSList *tok = NULL;
\r
443 GSList *lines = NULL;
\r
447 lines = (GSList*)event_info;
\r
448 if (1 != g_slist_length(lines)) {
\r
449 dbg("unsolicited msg but multiple line");
\r
452 line = (char*)(lines->data);
\r
453 dbg("on_bootup_event_sim_status notification : %s", line);
\r
455 tok = tcore_at_tok_new(line);
\r
456 value = atoi(g_slist_nth_data(tok, 0));
\r
459 dbg("SIM ready. request COPS & remove callback");
\r
460 dbg("power on done set for proactive command receiving mode");
\r
461 prepare_and_send_pending_request(tcore_object_ref_plugin(o), "sat", "AT+CFUN=6", NULL, TCORE_AT_NO_RESULT, on_response_enable_proactive_command);
\r
462 prepare_and_send_pending_request(tcore_object_ref_plugin(o), "umts_network", "AT+COPS=0", NULL, TCORE_AT_NO_RESULT, on_response_bootup_subscription);
\r
468 tcore_at_tok_free(tok);
\r
475 gboolean on_event_modem_power(TcoreAT *at, const char *line, TcorePlugin *p)
\r
477 CoreObject *o = NULL;
\r
478 struct treq_modem_set_flightmode flight_mode_set = {0};
\r
479 struct tnoti_modem_power modem_power = {0};
\r
480 TcoreHal *h = NULL;
\r
481 Storage *strg = NULL;
\r
483 o = tcore_plugin_ref_core_object(p, "modem");
\r
485 strg = tcore_server_find_storage(tcore_plugin_ref_server(p), "vconf");
\r
486 flight_mode_set.enable = tcore_storage_get_bool(strg, STORAGE_KEY_SETAPPL_FLIGHT_MODE_BOOL);
\r
488 h = tcore_object_get_hal(o);
\r
489 tcore_hal_set_power_state(h, TRUE);
\r
491 /* Set Flight mode as per AP settings */
\r
492 if (flight_mode_set.enable)
\r
494 prepare_and_send_pending_request(p, "modem", "AT+CFUN=4", NULL, TCORE_AT_NO_RESULT, on_response_set_flight_mode);
\r
495 tcore_modem_set_flight_mode_state(o, TRUE);
\r
499 prepare_and_send_pending_request(p, "modem", "AT+CFUN=1", NULL, TCORE_AT_NO_RESULT, on_response_set_flight_mode);
\r
500 tcore_modem_set_flight_mode_state(o, FALSE);
\r
504 prepare_and_send_pending_request(p, "modem", "AT+CGSN", NULL, TCORE_AT_NUMERIC, on_response_imei);
\r
506 /* Get Version Number */
\r
507 prepare_and_send_pending_request(p, "modem", "AT+CGMR", NULL, TCORE_AT_SINGLELINE, on_response_version);
\r
509 tcore_modem_set_powered(o, TRUE);
\r
511 modem_power.state = MODEM_STATE_ONLINE;
\r
513 tcore_server_send_notification(tcore_plugin_ref_server(tcore_object_ref_plugin(o)), o, TNOTI_MODEM_POWER,
\r
514 sizeof(struct tnoti_modem_power), &modem_power);
\r
519 static void _modem_subscribe_events(TcorePlugin *plugin)
\r
523 /* XCALLSTAT subscription */
\r
524 prepare_and_send_pending_request(plugin, "call", "at+xcallstat=1", NULL, TCORE_AT_NO_RESULT, on_response_bootup_subscription);
\r
526 /* XSIMSTATE subscription */
\r
527 prepare_and_send_pending_request(plugin, "sim", "at+xsimstate=1", NULL, TCORE_AT_NO_RESULT, on_response_bootup_subscription);
\r
529 prepare_and_send_pending_request(plugin, "umts_sms", "at+xsimstate=1", NULL, TCORE_AT_NO_RESULT, on_response_bootup_subscription);
\r
530 prepare_and_send_pending_request(plugin, "modem", "at+xsimstate=1", NULL, TCORE_AT_NO_RESULT, on_response_bootup_subscription);
\r
532 /* CREG subscription */
\r
533 prepare_and_send_pending_request(plugin, "umts_network", "at+creg=2", NULL, TCORE_AT_NO_RESULT, on_response_bootup_subscription);
\r
535 /* CGREG subscription */
\r
536 prepare_and_send_pending_request(plugin, "umts_network", "at+cgreg=2", NULL, TCORE_AT_NO_RESULT, on_response_bootup_subscription);
\r
538 /* Allow automatic time Zone updation via NITZ */
\r
539 prepare_and_send_pending_request(plugin, "umts_network", "at+ctzu=1", NULL, TCORE_AT_NO_RESULT, on_response_bootup_subscription);
\r
541 /* TZ, time & daylight changing event reporting subscription */
\r
542 prepare_and_send_pending_request(plugin, "umts_network", "at+ctzr=1", NULL, TCORE_AT_NO_RESULT, on_response_bootup_subscription);
\r
544 /* XMER subscription */
\r
545 prepare_and_send_pending_request(plugin, "umts_network", "at+xmer=1", NULL, TCORE_AT_NO_RESULT, on_response_bootup_subscription);
\r
547 /* CGEREP subscription */
\r
548 prepare_and_send_pending_request(plugin, "umts_ps", "at+cgerep=1", NULL, TCORE_AT_NO_RESULT, on_response_bootup_subscription);
\r
550 /* XDATASTAT subscription */
\r
551 prepare_and_send_pending_request(plugin, "umts_ps", "at+xdatastat=1", NULL, TCORE_AT_NO_RESULT, on_response_bootup_subscription);
\r
553 /* CSSN subscription */
\r
554 prepare_and_send_pending_request(plugin, "call", "at+cssn=1,1", NULL, TCORE_AT_NO_RESULT, on_response_bootup_subscription);
\r
556 /* CUSD subscription */
\r
557 prepare_and_send_pending_request(plugin, "call", "at+cusd=1", NULL, TCORE_AT_NO_RESULT, on_response_bootup_subscription);
\r
559 /* XDNS subscription */
\r
560 prepare_and_send_pending_request(plugin, "umts_ps", "at+xdns=1,1", NULL, TCORE_AT_NO_RESULT, on_response_bootup_subscription);
\r
562 /* CLIP subscription */
\r
563 prepare_and_send_pending_request(plugin, "call", "at+clip=1", NULL, TCORE_AT_NO_RESULT, on_response_bootup_subscription);
\r
565 /*CMEE subscription*/
\r
566 prepare_and_send_pending_request(plugin,"umts_ps","at+cmee=2",NULL,TCORE_AT_NO_RESULT, on_response_bootup_subscription);
\r
568 /*incoming sms and cb subscription*/
\r
569 prepare_and_send_pending_request(plugin,"umts_sms","at+cnmi=1,2,2,2,0",NULL,TCORE_AT_NO_RESULT, on_response_bootup_subscription);
\r
571 /* text/pdu mode subscription*/
\r
572 prepare_and_send_pending_request(plugin,"umts_sms","at+cmgf=0",NULL,TCORE_AT_NO_RESULT, on_response_last_bootup_subscription);
\r
579 static void on_response_setupmux(TcorePending *p, int data_len, const void *data, void *user_data)
\r
581 TcorePlugin *plugin = NULL;
\r
582 TcoreHal *hal = NULL;
\r
586 /* IMC Plugin dereferenced from pending request */
\r
587 plugin = tcore_pending_ref_plugin(p);
\r
589 /* Actual HAL - like svnet(2) */
\r
590 hal = (TcoreHal *)user_data;
\r
592 /* Initialize CMUX */
\r
593 ret = tcore_cmux_init(plugin, hal);
\r
594 if(TCORE_RETURN_SUCCESS == ret) {
\r
595 dbg("Successfully initialized CMUX");
\r
598 err("Failed to initialize CMUX");
\r
607 static void setup_mux(CoreObject *o)
\r
609 TcoreHal* hal = NULL;
\r
610 TcorePending *pending = NULL;
\r
613 /* HAL has type itself,
\r
614 * e.g.) TCORE_HAL_MODE_AT
\r
616 hal = tcore_object_get_hal(o);
\r
618 pending = tcore_at_pending_new(o, "AT+CMUX=0,0,,1509,10,3,30,,", "+CMUX", TCORE_AT_NO_RESULT, on_response_setupmux, hal);
\r
620 tcore_pending_set_send_callback(pending, on_confirmation_modem_message_send, NULL);
\r
622 /* Send callback */
\r
623 tcore_hal_send_request(hal, pending);
\r
629 static gboolean on_event_mux_channel_up(CoreObject *o, const void *event_info, void *user_data)
\r
631 TcorePlugin *plugin = NULL;
\r
634 plugin = (TcorePlugin *)user_data;
\r
635 _modem_subscribe_events(plugin);
\r
641 static void on_response_enable_logging(TcorePending *p, int data_len, const void *data, void *user_data)
\r
643 const TcoreATResponse *resp = data;
\r
644 TcorePlugin *plugin = NULL;
\r
646 plugin = tcore_pending_ref_plugin(p);
\r
648 /* DELETE ME: only for DEBUG */
\r
652 dbg("response...(result = %d, final_response = '%s')", resp->success, resp->final_response);
\r
655 dbg("RESPONSE OK");
\r
656 dbg("Enabling CP logging is success !!!\n");
\r
659 dbg("RESPONSE NOK");
\r
660 dbg("Enabling CP logging is failed !!!\n");
\r
663 dbg("Calling setup_mux");
\r
664 setup_mux(tcore_pending_ref_core_object(p));
\r
671 static void _send_enable_logging_command(CoreObject *o)
\r
673 TcoreATRequest *req = NULL;
\r
674 TcoreHal *hal = NULL;
\r
675 TcorePending *pending = NULL;
\r
679 dbg("Send Trace enabling command for CP logging. \n");
\r
682 dbg("Co-object is Null !!\n");
\r
686 hal = tcore_object_get_hal(o);
\r
687 pending = tcore_pending_new(o, 0);
\r
688 req = tcore_at_request_new("at+xsystrace=1,\"digrf=1;bb_sw=1;3g_sw=1\",\"digrf=0x84\",\"oct=4\";+xsystrace=11;+trace=1", NULL, TCORE_AT_NO_RESULT);
\r
690 dbg("cmd : %s, prefix(if any) :%s, cmd_len : %d", req->cmd, req->prefix, strlen(req->cmd));
\r
692 tcore_pending_set_request_data(pending, 0, req);
\r
693 tcore_pending_set_response_callback(pending, on_response_enable_logging, hal);
\r
694 tcore_pending_set_send_callback(pending, on_confirmation_modem_message_send, NULL);
\r
696 ret = tcore_hal_send_request(hal, pending);
\r
697 if(ret != TCORE_RETURN_SUCCESS)
\r
698 dbg("tcore_hal_send_request fail !!! (hal: 0x%x, pending: 0x%x)\n", hal, pending);
\r
702 static void on_response_poweron(TcorePending *p, int data_len, const void *data, void *user_data)
\r
704 const TcoreATResponse *resp = data;
\r
705 GSList*tokens=NULL;
\r
706 const char *line=NULL;
\r
707 gboolean bpoweron = FALSE;
\r
711 dbg("RESPONSE OK");
\r
712 /* Parse AT Response */
\r
714 line = (const char *)resp->lines->data;
\r
715 tokens = tcore_at_tok_new(line);
\r
716 if (g_slist_length(tokens) != 1) {
\r
717 dbg("invalid message");
\r
723 response = atoi(g_slist_nth_data(tokens, 0));
\r
725 dbg("CPAS: response %d",response);
\r
729 case CPAS_RES_READY:
\r
730 case CPAS_RES_RINGING:
\r
731 case CPAS_RES_CALL_PROGRESS:
\r
732 case CPAS_RES_ASLEEP:
\r
736 case CPAS_RES_UNAVAIL:
\r
737 case CPAS_RES_UNKNOWN:
\r
739 dbg("value is unvail/unknown - but CP responded - proceed poweron");
\r
740 //bpoweron = FALSE;
\r
745 dbg("CPAS: RESPONSE NOK");
\r
750 /* DELE ME: AT request & response are freed after AT processing in HAL.
\r
751 * ref.) _emit_pending_response (libtcore/src/at.c)
\r
754 tcore_at_tok_free(tokens);
\r
756 if(bpoweron == TRUE){
\r
757 dbg("Power on NOTI received, (pending: 0x%x, co: 0x%x)\n", p, tcore_pending_ref_core_object(p));
\r
759 _send_enable_logging_command(tcore_pending_ref_core_object(p));
\r
762 dbg("CP is not ready, let us send CPAS once again");
\r
763 s_modem_send_poweron(tcore_object_ref_plugin(tcore_pending_ref_core_object(p)));
\r
768 static TReturn power_off(CoreObject *o, UserRequest *ur)
\r
770 TcoreHal *hal = NULL;
\r
771 TcoreATRequest *req = NULL;
\r
772 TcorePending *pending = NULL;
\r
774 hal = tcore_object_get_hal(o);
\r
775 pending = tcore_pending_new(o, 0);
\r
777 req = tcore_at_request_new("AT+CFUN=0", NULL, TCORE_AT_NO_RESULT);
\r
779 dbg("cmd : %s, prefix(if any) :%s, cmd_len : %d", req->cmd, req->prefix, strlen(req->cmd));
\r
781 tcore_pending_set_request_data(pending, 0, req);
\r
782 tcore_pending_set_response_callback(pending, on_response_power_off, hal);
\r
783 tcore_pending_link_user_request(pending, ur);
\r
784 tcore_pending_set_send_callback(pending, on_confirmation_modem_message_send, NULL);
\r
786 tcore_hal_send_request(hal, pending);
\r
788 return TCORE_RETURN_SUCCESS;
\r
791 static TReturn get_imei(CoreObject *o, UserRequest *ur)
\r
794 TcoreATRequest *req;
\r
795 TcorePending *pending = NULL;
\r
797 hal = tcore_object_get_hal(o);
\r
798 pending = tcore_pending_new(o, 0);
\r
800 req = tcore_at_request_new("AT+CGSN", NULL, TCORE_AT_NUMERIC);
\r
802 dbg("cmd : %s, prefix(if any) :%s, cmd_len : %d", req->cmd, req->prefix, strlen(req->cmd));
\r
804 tcore_pending_set_request_data(pending, 0, req);
\r
805 tcore_pending_set_response_callback(pending, on_response_imei, hal);
\r
806 tcore_pending_link_user_request(pending, ur);
\r
807 tcore_pending_set_send_callback(pending, on_confirmation_modem_message_send, NULL);
\r
809 tcore_hal_send_request(hal, pending);
\r
811 return TCORE_RETURN_SUCCESS;
\r
815 static TReturn get_version(CoreObject *o, UserRequest *ur)
\r
818 TcoreATRequest *req;
\r
819 TcorePending *pending = NULL;
\r
821 hal = tcore_object_get_hal(o);
\r
822 pending = tcore_pending_new(o, 0);
\r
824 req = tcore_at_request_new("AT+CGMR", NULL, TCORE_AT_SINGLELINE);
\r
826 dbg("cmd : %s, prefix(if any) :%s, cmd_len : %d", req->cmd, req->prefix, strlen(req->cmd));
\r
828 tcore_pending_set_request_data(pending, 0, req);
\r
829 tcore_pending_set_response_callback(pending, on_response_version, hal);
\r
830 tcore_pending_link_user_request(pending, ur);
\r
831 tcore_pending_set_send_callback(pending, on_confirmation_modem_message_send, NULL);
\r
833 tcore_hal_send_request(hal, pending);
\r
835 return TCORE_RETURN_SUCCESS;
\r
838 static TReturn set_flight_mode(CoreObject *o, UserRequest *ur)
\r
840 TcoreHal *hal = NULL;
\r
841 TcoreATRequest *req = NULL;
\r
842 TcorePending *pending = NULL;
\r
843 const struct treq_modem_set_flightmode *req_data = NULL;
\r
844 char *cmd_str = NULL;
\r
846 hal = tcore_object_get_hal(o);
\r
847 pending = tcore_pending_new(o, 0);
\r
849 req_data = tcore_user_request_ref_data(ur, NULL);
\r
851 if (req_data->enable) {
\r
852 dbg("Flight mode on/n");
\r
853 cmd_str = g_strdup("AT+CFUN=4");
\r
856 dbg("Flight mode off/n");
\r
857 cmd_str = g_strdup("AT+CFUN=1");
\r
860 req = tcore_at_request_new((const char*)cmd_str, NULL, TCORE_AT_NO_RESULT);
\r
862 dbg("cmd : %s, prefix(if any) :%s, cmd_len : %d", req->cmd, req->prefix, strlen(req->cmd));
\r
864 tcore_pending_set_request_data(pending, 0, req);
\r
865 tcore_pending_set_response_callback(pending, on_response_set_flight_mode, hal);
\r
866 tcore_pending_link_user_request(pending, ur);
\r
867 tcore_pending_set_send_callback(pending, on_confirmation_modem_message_send, NULL);
\r
869 tcore_hal_send_request(hal, pending);
\r
871 return TCORE_RETURN_SUCCESS;
\r
875 static struct tcore_modem_operations modem_ops =
\r
878 .power_off = power_off,
\r
879 .power_reset = NULL,
\r
880 .set_flight_mode = set_flight_mode,
\r
881 .get_imei = get_imei,
\r
882 .get_version = get_version,
\r
884 .dun_pin_ctrl = NULL,
\r
887 gboolean s_modem_init(TcorePlugin *p, TcoreHal *h)
\r
889 CoreObject *o = NULL;
\r
890 GQueue *work_queue = NULL;
\r
891 TelMiscVersionInformation *vi_property = NULL;
\r
892 TelMiscSNInformation *imei_property = NULL;
\r
893 TelMiscSNInformation *sn_property = NULL;
\r
895 o = tcore_modem_new(p, "modem", &modem_ops, h);
\r
899 work_queue = g_queue_new();
\r
900 tcore_object_link_user_data(o, work_queue);
\r
902 vi_property = calloc(sizeof(TelMiscVersionInformation), 1);
\r
903 tcore_plugin_link_property(p, "VERSION", vi_property);
\r
905 imei_property = calloc(sizeof(TelMiscSNInformation), 1);
\r
906 tcore_plugin_link_property(p, "IMEI", imei_property);
\r
908 sn_property = calloc(sizeof(TelMiscSNInformation), 1);
\r
909 tcore_plugin_link_property(p, "SN", sn_property);
\r
911 dbg("Registerind for CMUX-UP event");
\r
912 tcore_object_add_callback(o, "CMUX-UP", on_event_mux_channel_up, p);
\r
914 dbg("Registering for +XSIM event");
\r
915 tcore_object_add_callback(o, "+XSIM", on_event_bootup_sim_status, NULL);
\r
920 void s_modem_exit(TcorePlugin *p)
\r
922 CoreObject *o = NULL;
\r
923 GQueue *work_queue = NULL;
\r
924 TelMiscVersionInformation *vi_property = NULL;
\r
925 TelMiscSNInformation *imei_property = NULL;
\r
926 TelMiscSNInformation *sn_property = NULL;
\r
931 o = tcore_plugin_ref_core_object(p, "modem");
\r
933 work_queue = tcore_object_ref_user_data(o);
\r
934 g_queue_free(work_queue);
\r
936 vi_property = tcore_plugin_ref_property(p, "VERSION");
\r
940 imei_property = tcore_plugin_ref_property(p, "IMEI");
\r
942 free(imei_property);
\r
944 sn_property = tcore_plugin_ref_property(p, "SN");
\r
948 tcore_modem_free(o);
\r
952 gboolean s_modem_send_poweron(TcorePlugin *p)
\r
955 TcoreATRequest *req;
\r
956 TcorePending *pending = NULL;
\r
959 o = tcore_plugin_ref_core_object(p, "modem");
\r
960 hal = tcore_object_get_hal(o);
\r
962 pending = tcore_pending_new(o, 0);
\r
964 req = tcore_at_request_new("AT+CPAS", "+CPAS", TCORE_AT_SINGLELINE);
\r
966 dbg("cmd : %s, prefix(if any) :%s, cmd_len : %d", req->cmd, req->prefix, strlen(req->cmd));
\r
968 tcore_pending_set_timeout(pending, 10);
\r
969 tcore_pending_set_priority(pending, TCORE_PENDING_PRIORITY_DEFAULT);
\r
970 tcore_pending_set_timeout_callback(pending, on_timeout_modem_poweron, hal);
\r
972 tcore_pending_set_request_data(pending, 0, req);
\r
973 tcore_pending_set_response_callback(pending, on_response_poweron, hal);
\r
974 tcore_pending_set_send_callback(pending, on_confirmation_modem_message_send, NULL);
\r
976 tcore_hal_send_request(hal, pending);
\r