blob: 29643dbcdf8d2dbd6f2b594425e73f16fb65fa50 [file] [log] [blame]
/* Copyright Statement:
*
* This software/firmware and related documentation ("MediaTek Software") are
* protected under relevant copyright laws. The information contained herein
* is confidential and proprietary to MediaTek Inc. and/or its licensors.
* Without the prior written permission of MediaTek inc. and/or its licensors,
* any reproduction, modification, use or disclosure of MediaTek Software,
* and information contained herein, in whole or in part, shall be strictly prohibited.
*/
/* MediaTek Inc. (C) 2010. All rights reserved.
*
* BY OPENING THIS FILE, RECEIVER HEREBY UNEQUIVOCALLY ACKNOWLEDGES AND AGREES
* THAT THE SOFTWARE/FIRMWARE AND ITS DOCUMENTATIONS ("MEDIATEK SOFTWARE")
* RECEIVED FROM MEDIATEK AND/OR ITS REPRESENTATIVES ARE PROVIDED TO RECEIVER ON
* AN "AS-IS" BASIS ONLY. MEDIATEK EXPRESSLY DISCLAIMS ANY AND ALL WARRANTIES,
* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE IMPLIED WARRANTIES OF
* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE OR NONINFRINGEMENT.
* NEITHER DOES MEDIATEK PROVIDE ANY WARRANTY WHATSOEVER WITH RESPECT TO THE
* SOFTWARE OF ANY THIRD PARTY WHICH MAY BE USED BY, INCORPORATED IN, OR
* SUPPLIED WITH THE MEDIATEK SOFTWARE, AND RECEIVER AGREES TO LOOK ONLY TO SUCH
* THIRD PARTY FOR ANY WARRANTY CLAIM RELATING THERETO. RECEIVER EXPRESSLY ACKNOWLEDGES
* THAT IT IS RECEIVER'S SOLE RESPONSIBILITY TO OBTAIN FROM ANY THIRD PARTY ALL PROPER LICENSES
* CONTAINED IN MEDIATEK SOFTWARE. MEDIATEK SHALL ALSO NOT BE RESPONSIBLE FOR ANY MEDIATEK
* SOFTWARE RELEASES MADE TO RECEIVER'S SPECIFICATION OR TO CONFORM TO A PARTICULAR
* STANDARD OR OPEN FORUM. RECEIVER'S SOLE AND EXCLUSIVE REMEDY AND MEDIATEK'S ENTIRE AND
* CUMULATIVE LIABILITY WITH RESPECT TO THE MEDIATEK SOFTWARE RELEASED HEREUNDER WILL BE,
* AT MEDIATEK'S OPTION, TO REVISE OR REPLACE THE MEDIATEK SOFTWARE AT ISSUE,
* OR REFUND ANY SOFTWARE LICENSE FEES OR SERVICE CHARGE PAID BY RECEIVER TO
* MEDIATEK FOR SUCH MEDIATEK SOFTWARE AT ISSUE.
*
* The following software/firmware and/or related documentation ("MediaTek Software")
* have been modified by MediaTek Inc. All revisions are subject to any receiver's
* applicable license agreements with MediaTek Inc.
*/
#include "stk.h"
#include <vendor-ril/telephony/ril.h>
#include <stdlib.h>
#include <stdio.h>
#include <cutils/jstring.h>
#include <string.h>
#include <time.h>
#include "resp_timeout.h"
#undef LOG_TAG
#define LOG_TAG "DEMO_STK"
#define INVALID -1;
#define ACCEPT 1;
#define REJECT 0;
extern void ARspRequestWithArg(int request, const char* arg,RIL_SOCKET_ID socket_id);
//RIL_REQUEST_STK_SEND_ENVELOPE_COMMAND
int sendEnvelope(int argc, char **argv, RIL_SOCKET_ID socket_id, RequestInfo *pRI)
{
android::Parcel p;
size_t pos = p.dataPosition();
//p.writeString(contents);
writeStringToParcel(p, (const char *)argv[1]);
p.setDataPosition(pos);
pRI->pCI->dispatchFunction(p, pRI);
return 0;
}
//RIL_REQUEST_STK_SEND_TERMINAL_RESPONSE
int sendTerminalResponse(int argc, char **argv, RIL_SOCKET_ID socket_id, RequestInfo *pRI)
{
android::Parcel p;
size_t pos = p.dataPosition();
//p.writeString(contents);
writeStringToParcel(p, (const char *)argv[1]);
p.setDataPosition(pos);
pRI->pCI->dispatchFunction(p, pRI);
return 0;
}
//RIL_REQUEST_STK_SEND_ENVELOPE_WITH_STATUS
int sendEnvelopeWithStatus(int argc, char **argv, RIL_SOCKET_ID socket_id, RequestInfo *pRI)
{
android::Parcel p;
size_t pos = p.dataPosition();
//p.writeString(contents);
writeStringToParcel(p, (const char *)argv[1]);
p.setDataPosition(pos);
pRI->pCI->dispatchFunction(p, pRI);
return 0;
}
//RIL_REQUEST_STK_HANDLE_CALL_SETUP_REQUESTED_FROM_SIM
int handleCallSetupRequestFromSim(int argc, char **argv, RIL_SOCKET_ID socket_id, RequestInfo *pRI)
{
if(argc != 2) {
free(pRI);
RLOGD("handleCallSetupRequestFromSim parameter lost");
return 0;
}
int reject = INVALID;
if(strcasecmp("yes", argv[1])){
reject = ACCEPT;
} else if (strcasecmp("no", argv[1])){
reject = REJECT;
} else {
free(pRI);
RLOGD("input: %s, parameter is wrong, please input again!", argv[1]);
return 0;
}
android::Parcel p;
size_t pos = p.dataPosition();
p.writeInt32(1);
p.writeInt32(reject);
p.setDataPosition(pos);
pRI->pCI->dispatchFunction(p, pRI);
clear_timeout(socket_id);
return 0;
}
//RIL_REQUEST_REPORT_STK_SERVICE_IS_RUNNING
int reportStkServiceIsRunning(int argc, char **argv, RIL_SOCKET_ID socket_id, RequestInfo *pRI)
{
android::Parcel p;
pRI->pCI->dispatchFunction(p, pRI);
return 0;
}
static int getStkCommandType(char *cmd) {
char temp[3] = {0};
int cmdType = 0;
strncpy(temp, cmd, 2);
cmdType = strtoul(temp, NULL, 16);
cmdType = 0xFF & cmdType;
return cmdType;
}
static void parseStkCmdType(char* cmd, int* cmdType) {
int cmd_len = strlen(cmd);
int typePos = 0;
if (cmd_len < 14) {
RLOGD("parseStkCmdType exception!");
return;
}
if(cmd[2] <= '7' ) {
typePos = 10;
} else {
typePos = 12;
}
// get command type
*cmdType = getStkCommandType(&cmd[typePos]);
}
static void parseStkCmdQualifier(char* cmd, int* cmdQual) {
int cmd_len = strlen(cmd);
int typePos = 0;
if (cmd_len < 14) {
RLOGD("parseStkCmdQualifier exception!");
return;
}
if(cmd[2] <= '7' ) {
typePos = 12;
} else {
typePos = 14;
}
// get command qualifier
*cmdQual = getStkCommandType(&cmd[typePos]);
}
static int getStkCommandNumber(char *cmd) {
char temp[3] = {0};
int cmdNum = 0;
strncpy(temp, cmd, 2);
cmdNum = strtoul(temp, NULL, 16);
cmdNum = 0xFF & cmdNum;
return cmdNum;
}
static void parseStkCmdNum(char* cmd, int* cmdNum) {
int cmd_len = strlen(cmd);
int typePos = 0;
if (cmd_len < 12) {
RLOGD("parseStkCmdNum exception!");
return;
}
if (cmd[2] <= '7') {
typePos = 8;
} else {
typePos = 10;
}
// check command num
*cmdNum = getStkCommandNumber(&cmd[typePos]);
RLOGD("parseStkCmdNum cmdNum:%d", *cmdNum);
}
static int numToBCD(int data) {
char string[20] = {0};
int low = 0;
int high = 0;
int result = -1;
char num_table[10] = {'0', '1', '2', '3', '4', '5', '6', '7', '8', '9'};
snprintf(string, 20, "%2d", data);
if(strlen(string)>2) {
RLOGD("[numToBCD]Out of range, data = %d, string = %s", data, string);
return -1;
}
for(int i=0; i<10; i++) {
if(num_table[i] == string[0])
low = i ;
if(num_table[i] == string[1])
high = i;
}
result = ((high<<4)&0xF0)+(low&0x0F);
RLOGD("[numToBCD]data=%d, result=%#x, string=%s, low=%d, high=%d", data, result, string, low, high);
return result;
}
static void handleProvideLocalInfo(char *cmd, int slot_id){
int cmdNum = -1;
time_t now_tmp;
struct tm *now;
int year = -1, year_bcd = -1;
int month = -1, month_bcd = -1;
int day = -1, day_bcd = -1;
int hour = -1, hour_bcd = -1;
int min = -1, min_bcd = -1;
int sec = -1, sec_bcd = -1;
char response[200]="";
parseStkCmdNum(cmd, &cmdNum);
time(&now_tmp);
now = localtime(&now_tmp);
year = now->tm_year + 1900-2000;
month = now->tm_mon+1;
day = now->tm_mday;
hour = now->tm_hour;
min = now->tm_min;
sec = now->tm_sec;
RLOGD("[handleProvideLocalInfo]Get time from system: %d/%d/%d, %d:%d:%d", year, month, day, hour, min, sec);
year_bcd = numToBCD(year);
month_bcd = numToBCD(month);
day_bcd = numToBCD(day);
hour_bcd = numToBCD(hour);
min_bcd = numToBCD(min);
sec_bcd = numToBCD(sec);
snprintf(response, 200, "8103%02X260382028281830100A607%02X%02X%02X%02X%02X%02XFF", cmdNum&0XFF, year_bcd&0XFF, month_bcd&0XFF,
day_bcd&0XFF, hour_bcd&0XFF, min_bcd&0XFF, sec_bcd&0XFF);
RLOGD("[handleProvideLocalInfo]Send RIL_REQUEST_STK_SEND_TERMINAL_RESPONSE, data=%s", response);
ARspRequestWithArg(RIL_REQUEST_STK_SEND_TERMINAL_RESPONSE, response, (RIL_SOCKET_ID)slot_id);
}
void handleStkCommand(char* response, int responselen, int slot_id) {
int cmdType = -1;
int cmdQual = -1;
int cmdNum = -1;
parseStkCmdType(response, &cmdType);
parseStkCmdQualifier(response, &cmdQual);
parseStkCmdNum(response, &cmdNum);
RLOGD("[handleStkCommand][slot%d]cmdType=%d, cmdQual=%d, cmdNum=%d", slot_id, cmdType, cmdQual, cmdNum);
switch (cmdType)
{
case CMD_OPEN_CHAN:
RLOGD("[URC][CAT][BIP][SIM%d]: the proactive command include open channel TLV, please choose yes or no", slot_id);
printf("[URC][CAT][BIP][SIM%d]: the proactive command include open channel TLV, please choose yes or no\n", slot_id+1);
setup_timeout(slot_id); //set up timeout one minutes
break;
case CMD_PROVIDE_LOCAL_INFO:
if (0x03 != cmdQual){
RLOGD("not request for data/time, qualifier = %#x", cmdQual);
return;
}
handleProvideLocalInfo(response, slot_id);
break;
default:
break;
}
}