blob: 2c2cddeb876ee63c3c8e2cecc5f680a19f075822 [file] [log] [blame]
// SPDX-License-Identifier: MediaTekProprietary
/*
* Copyright (C) 2006 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
#include <string.h>
#include <stddef.h>
#include <stdlib.h>
#include <stdio.h>
#include <stdbool.h>
#include<fcntl.h>
#include<sys/stat.h>
#include<sys/types.h>
#include<unistd.h>
#include <assert.h>
#include <log/log.h>
#include <vendor-ril/telephony/ril.h>
#include <string>
#include <mutex>
#include <vector>
#include <cutils/properties.h>
#include "Radio_capability_switch_util.h"
#include "common.h"
#include "Phone_utils.h"
#include "utils.h"
#include "data.h"
#include "cc.h"
#include "include/lynq_systime.h"
#include <include/lynq_uci.h>
#ifdef LED_SUPPORT
#include "led.h"
#endif
#include "lynq_shm.h"
static pthread_mutex_t s_DataMutex = PTHREAD_MUTEX_INITIALIZER;
static pthread_cond_t s_DataCond = PTHREAD_COND_INITIALIZER;
#undef LOG_TAG
#define LOG_TAG "DEMO_COMMON"
#define UNKOWN_VALUE (-1)
/*Warren add for FAW 2021/11/1 start*/
extern int ttyGS3_fd = -1;
/*Warren add for FAW 2021/11/1 end*/
typedef enum {
STATE_IN_SERVICE =0,
STATE_OUT_OF_SERVICE =1,
STATE_EMERGENCY_ONLY =2,
STATE_POWER_OFF =3
} Service_State;
RfDesenseTxTest* m_RfDesense;
static RIL_CardStatus_v6* cur_CardS_Status[2] = {NULL, NULL};
static RIL_RadioCapability radio_capability[2];
static int cur_voice_radio_tech[2] = {RADIO_TECH_UNKNOWN, RADIO_TECH_UNKNOWN};
static int reg_voice_service_state[2] = {0, 0};
static int reg_data_service_state[2] = {0, 0};
static int reg_data_radio_tech[2] = {RADIO_TECH_UNKNOWN, RADIO_TECH_UNKNOWN};
static int reg_voice_radio_tech[2] = {RADIO_TECH_UNKNOWN, RADIO_TECH_UNKNOWN};
static int preferred_network_type[2] = {Phone_utils::PREFERRED_NETWORK_MODE, Phone_utils::PREFERRED_NETWORK_MODE};
static int radio_status[2] = {RADIO_STATE_UNAVAILABLE, RADIO_STATE_UNAVAILABLE};
static std::vector<int> call_state[2];
static int default_sim_all = RIL_SOCKET_1;
static int default_sim_all_except_data = RIL_SOCKET_1;
static int default_sim_voice = RIL_SOCKET_1;
static int default_sim_data = RIL_SOCKET_1;
static int default_sim_sms = RIL_SOCKET_1;
static bool isNeedReconnect = false;
static std::int32_t token = 0;
static std::mutex g_mutex;
pthread_mutex_t s_state_change_mutex = PTHREAD_MUTEX_INITIALIZER;
pthread_cond_t s_state_change_cond = PTHREAD_COND_INITIALIZER;
/*Warren add for SZZT 2021/11/14 start*
** record data registration
*/
extern int current_data_reg = -1;
extern int modemStatus = 0;
/*Warren add for SZZT 2021/11/14 end*/
int g_ril_test;
/*hq add for key information output start 2022/03/01*/
// extern int lynq_output_LINFO_enable =0;
// typedef enum {
// RADIO_NW_2G = 0,
// RADIO_NW_3G = 1,
// RADIO_NW_4G = 2,
// #ifdef TELEMATIC_5G_SUPPORT
// RADIO_NW_5G = 3,
// #endif
// } RIL_RadioNW;
// const char * cardStateToString(int cardStatus)
// {
// switch(cardStatus) {
// case RIL_CARDSTATE_ABSENT:
// return "absent";
// case RIL_CARDSTATE_PRESENT:
// return "present";
// case RIL_CARDSTATE_ERROR:
// return "error";
// default:
// return "unknown";
// }
// }
// const char * serviceStateToString(int service_state)
// {
// switch(service_state) {
// case STATE_IN_SERVICE:
// return "IN SERVICE";
// case STATE_OUT_OF_SERVICE:
// return "OUT OF SERVICE";
// case STATE_POWER_OFF:
// return "POWER_OFF";
// case STATE_EMERGENCY_ONLY:
// return "EMERGENCY_ONLY";
// case UNKOWN_VALUE:
// return "unDefined";
// default:
// return "unDefined";
// }
// }
// const char * RadioNwToString(int radio_nw)
// {
// switch(radio_nw) {
// case RADIO_NW_2G:
// return "2G";
// case RADIO_NW_3G:
// return "3G";
// case RADIO_NW_4G:
// return "4G";
// #ifdef TELEMATIC_5G_SUPPORT
// case RADIO_NW_5G:
// return "5G";
// #endif
// case UNKOWN_VALUE:
// return "unknown";
// default:
// return "unknown";
// }
// }
// const char * preferredNetworkTypeToString(int preferred_network_type)
// {
// switch(preferred_network_type) {
// case PREF_NET_TYPE_GSM_WCDMA /*0*/ : return " GSM/WCDMA (WCDMA case PREFerred)";
// case PREF_NET_TYPE_GSM_ONLY : return " GSM only";
// case PREF_NET_TYPE_WCDMA : return " WCDMA ";
// case PREF_NET_TYPE_GSM_WCDMA_AUTO : return " GSM/WCDMA (auto mode, according to PRL)";
// case PREF_NET_TYPE_CDMA_EVDO_AUTO : return " CDMA and EvDo (auto mode, according to PRL)";
// case PREF_NET_TYPE_CDMA_ONLY : return " CDMA only";
// case PREF_NET_TYPE_EVDO_ONLY : return " EvDo only";
// case PREF_NET_TYPE_GSM_WCDMA_CDMA_EVDO_AUTO : return " GSM/WCDMA, CDMA, and EvDo (auto mode, according to PRL)";
// case PREF_NET_TYPE_LTE_CDMA_EVDO : return " LTE, CDMA and EvDo";
// case PREF_NET_TYPE_LTE_GSM_WCDMA : return " LTE, GSM/WCDMA";
// case PREF_NET_TYPE_LTE_CMDA_EVDO_GSM_WCDMA : return " LTE, CDMA, EvDo, GSM/WCDMA";
// case PREF_NET_TYPE_LTE_ONLY : return " LTE only";
// case PREF_NET_TYPE_LTE_WCDMA /*12*/ : return " LTE/WCDMA";
// case PREF_NET_TYPE_LTE_GSM /*30*/ : return " LTE/GSM";
// case PREF_NET_TYPE_LTE_TDD_ONLY /*31*/ : return " LTE only";
// case 13: return "TD-SCDMA only";
// case 14: return "TD-SCDMA and WCDMA";
// case 15: return "TD-SCDMA and LTE";
// case 16: return "TD-SCDMA and GSM";
// case 17: return "TD-SCDMA,GSM and LTE";
// case 18: return "TD-SCDMA, GSM/WCDMA";
// case 19: return "TD-SCDMA, WCDMA and LTE";
// case 20: return "TD-SCDMA, GSM/WCDMA and LTE";
// case 21: return "TD-SCDMA,EvDo,CDMA,GSM/WCDMA";
// case 22: return "TD-SCDMA/LTE/GSM/WCDMA, CDMA, and EvDo";
// //case 30: return "LTE/GSM";
// //case 31: return "LTE TDD Only mode";
// case 32: return "CDMA,GSM(2G Global)";
// case 33: return "CDMA,EVDO,GSM";
// case 34: return "LTE,CDMA,EVDO,GSM(4G Global, 4M)";
// default:
// return "unDefined";
// }
// }
/*hq add for key information output end*/
static int regCodeToRadioTechnology(int request, int code, int slot);
void lynq_output_info(const char* format,...)
{
if(ttyGS3_fd < 0)
{
return;
}
char buf[1024] = {0};
int n;
va_list args;
va_start(args, format);
vsnprintf(buf, sizeof(buf), format, args);
va_end(args);
n=write(ttyGS3_fd, buf, strlen(buf));
if(n < 0)
{
perror("lynq resp write:");
}
return;
}
void update_call_state(void *response, size_t responselen, int slot) {
int num = responselen / sizeof(RIL_Call *);
if(num == 0) {
call_state[slot].clear();
RLOGD("[SIM%d]clear call state", slot);
} else {
call_state[slot].clear();
for (int i = 0 ; i < num ; i++) {
RIL_Call *p_cur = ((RIL_Call **) response)[i];
/* each call info */
call_state[slot].push_back(p_cur->state);
RLOGD("[SIM%d][id:%d]update_call_state: %d", slot,p_cur->index, p_cur->state);
}
}
}
int is_call_state_idle(int slot) {
bool is_idle = true;
if(!call_state[slot].empty()) {
is_idle = false;
}
RLOGD("[SIM%d]is_call_state_idle: %d", slot, is_idle);
return is_idle;
}
void update_preferred_network_type(int type, int slot) {
RLOGD("[SIM%d]update_preferred_network_type: %d", slot, type);
preferred_network_type[slot] = type;
}
int get_preferred_network_type(int slot) {
return preferred_network_type[slot];
}
static int needBlockReq(int request)
{
#ifdef ENABLE_BLOCK_FEATURE
return 1;
#endif
switch (request){
case RIL_REQUEST_RADIO_POWER: return 1;
case RIL_REQUEST_SET_IMS_ENABLE: return 1;
//case RIL_REQUEST_DATA_REGISTRATION_STATE: return 1;
default: return 0;
}
return 0;
}
static int setupToken(int token, int mode, int block)
{
switch (mode){
case INIT:
token |= INIT_TOKEN_MARK;
break;
case UDP:
token |= RIL_TOKEN_MARK;
break;
case ATCI:
token |= ATCI_TOKEN_MARK;
break;
case RSPD:
token |= RSP_DISP_TOKEN_MARK;
break;
case OTHER:
token |= OTHER_TOKEN_MARK;
break;
default:
break;
}
if(block)
token |= BLOCK_MARK;
return token;
}
bool isDataConnectEnable(int slot) {
char value[PROPERTY_VALUE_MAX] = {0};
utils::getMSimProperty(slot,PROP_DEFAULT_DATA_SIM_STATUS, value);
if(atoi(value) == 1) {
return true;
}
return false;
}
void updataDataConnectState(int slot, bool state) {
utils::setMSimProperty(slot,PROP_DEFAULT_DATA_SIM_STATUS, const_cast<char*>(state ? "1":"0"));
}
std::int32_t GenerateToken(int mode, int request) {
g_mutex.lock();
if (token +1 == TOKEN_MODE) {
token = 1;
} else {
token++;
}
std::int32_t t= 0;
t = setupToken(token,mode,needBlockReq(request));
g_mutex.unlock();
return t;
}
RequestInfo* creatRILInfoAndInit(int request, int mode, RIL_SOCKET_ID soc_id)
{
RequestInfo *pRI = (RequestInfo *)calloc(1, sizeof(RequestInfo));
if(pRI ==NULL){
RLOGE("%s,memory alloc error!",__func__);
return NULL;
}
android::initRequestInfo(pRI,request,mode, soc_id);
return pRI;
}
void set_default_sim_all_except_data(int slot_id) {
RLOGD("set_default_sim_all excpet data: %d", slot_id);
default_sim_all_except_data = slot_id;
set_default_sim_voice(slot_id);
set_default_sim_sms(slot_id);
}
int get_default_sim_all_except_data() {
return default_sim_all_except_data;
}
void set_default_sim_all(int slot_id){
RLOGD("set_default_sim_all: %d", slot_id);
default_sim_all = slot_id;
set_default_sim_all_except_data(slot_id);
set_default_sim_data(slot_id);
}
int get_default_sim_all(){
return default_sim_all;
}
void set_default_sim_voice(int slot_id){
RLOGD("set_default_sim_voice: %d", slot_id);
default_sim_voice = slot_id;
}
void lynq_send_result_already(void)
{
RLOGD("send_imei_state_change");
pthread_mutex_lock(&s_state_change_mutex);
pthread_cond_signal(&s_state_change_cond);
pthread_mutex_unlock(&s_state_change_mutex);
}
void lynq_wait_result_comeback(int mtime)
{
RLOGD("wait_call_state");
int sec = 0;
int usec = 0;
struct timeval now;
struct timespec timeout;
gettimeofday(&now,NULL);
sec = mtime/1000;
usec = mtime%1000;
timeout.tv_sec = now.tv_sec+sec;
timeout.tv_nsec = now.tv_usec*1000+usec*1000000;
pthread_mutex_lock(&s_state_change_mutex);
pthread_cond_timedwait(&s_state_change_cond,&s_state_change_mutex,&timeout);
pthread_mutex_unlock(&s_state_change_mutex);
RLOGD("wait_call_state end");
}
int get_default_sim_voice(){
return default_sim_voice;
}
void set_default_sim_data(int slot) {
RLOGD("set_default_sim_data: %d", slot);
pthread_mutex_lock(&s_DataMutex);
if(get_default_sim_data() != slot) {
if(isDataConnectEnable(get_default_sim_data())) {
isNeedReconnect = true;
deactivateDataCall(0,NULL,(RIL_SOCKET_ID)0,NULL);
RLOGD("set_default_sim_data, wait deactive data call done");
pthread_cond_wait(&s_DataCond, &s_DataMutex);
RLOGD("set_default_sim_data, deactive data call done");
}
RLOGD("set_default_sim_data, set prop");
default_sim_data = slot;
utils::mtk_property_set(PROP_DEFAULT_DATA_SIM, std::to_string(default_sim_data + 1).c_str());
while(!isRadioAvailable(RIL_SOCKET_ID(slot))) {
sleep(1);
RLOGD("[SIM%d]set_default_sim_data(RIL_REQUEST_SET_RADIO_CAPABILITY): wait radio available", slot);
}
syncDataSettings(RIL_SOCKET_ID(slot));
if(utils::is_support_dsds()) {
Radio_capability_switch_util::sendRadioCapabilityRequest(slot);
}
}
pthread_mutex_unlock(&s_DataMutex);
}
bool isNeedConnect() {
return isNeedReconnect;
}
void resetConnect() {
isNeedReconnect = false;
}
int get_default_sim_data_for_switch() {
return default_sim_data;
}
int get_default_sim_data(){
default_sim_data = utils::mtk_property_get_int32(PROP_DEFAULT_DATA_SIM, 1) -1;
return default_sim_data;
}
void set_default_sim_sms(int slot_id){
RLOGD("set_default_sim_sms: %d", slot_id);
default_sim_sms = slot_id;
}
int get_default_sim_sms() {
return default_sim_sms;
}
static int regCodeToServiceState(int request,int code, int slot);
const char * radioStateToString(RIL_RadioState s) {
switch (s) {
case RADIO_STATE_OFF:
return "RADIO_OFF";
case RADIO_STATE_UNAVAILABLE:
return "RADIO_UNAVAILABLE";
case RADIO_STATE_SIM_NOT_READY:
return "RADIO_SIM_NOT_READY";
case RADIO_STATE_SIM_LOCKED_OR_ABSENT:
return "RADIO_SIM_LOCKED_OR_ABSENT";
case RADIO_STATE_SIM_READY:
return "RADIO_SIM_READY";
case RADIO_STATE_RUIM_NOT_READY:
return "RADIO_RUIM_NOT_READY";
case RADIO_STATE_RUIM_READY:
return "RADIO_RUIM_READY";
case RADIO_STATE_RUIM_LOCKED_OR_ABSENT:
return "RADIO_RUIM_LOCKED_OR_ABSENT";
case RADIO_STATE_NV_NOT_READY:
return "RADIO_NV_NOT_READY";
case RADIO_STATE_NV_READY:
return "RADIO_NV_READY";
case RADIO_STATE_ON:
return "RADIO_ON";
default:
return "<unknown state>";
}
}
const char *rilSocketIdToString(RIL_SOCKET_ID socket_id) {
switch (socket_id) {
case RIL_SOCKET_1:
return "RIL_SOCKET_1";
#if (SIM_COUNT >= 2)
case RIL_SOCKET_2:
return "RIL_SOCKET_2";
#endif
#if (SIM_COUNT >= 3)
case RIL_SOCKET_3:
return "RIL_SOCKET_3";
#endif
#if (SIM_COUNT >= 4)
case RIL_SOCKET_4:
return "RIL_SOCKET_4";
#endif
default:
return "not a valid RIL";
}
}
void update_radio_capa(RIL_RadioCapability* cap, int slot) {
memset(&radio_capability[slot], 0, sizeof(RIL_RadioCapability));
if(cap != NULL) {
strcpy(radio_capability[slot].logicalModemUuid,cap->logicalModemUuid);
radio_capability[slot].phase = cap->phase;
radio_capability[slot].rat = cap->rat;
radio_capability[slot].session = cap->session;
radio_capability[slot].status = cap->status;
radio_capability[slot].version = cap->version;
}
}
RIL_RadioCapability get_radio_capa(int slot) {
return radio_capability[slot];
}
void update_voice_radio_tech(int code, int slot) {
cur_voice_radio_tech[slot] = code;
}
int get_voice_radio_tech(int slot){
return cur_voice_radio_tech[slot];
}
void updateCardStatusV6(RIL_CardStatus_v6 *card_status,int slot)
{
if(cur_CardS_Status[slot] != NULL) {
RLOGD("[slot%d]updateCardStatusV6", slot);
for(int i = 0; i < cur_CardS_Status[slot]->num_applications; i++) {
free(cur_CardS_Status[slot]->applications[i].aid_ptr);
cur_CardS_Status[slot]->applications[i].aid_ptr = NULL;
free(cur_CardS_Status[slot]->applications[i].app_label_ptr);
cur_CardS_Status[slot]->applications[i].app_label_ptr = NULL;
}
free(cur_CardS_Status[slot]);
cur_CardS_Status[slot] = NULL;
}
cur_CardS_Status[slot] = (RIL_CardStatus_v6 *)calloc(1, sizeof(RIL_CardStatus_v6));
memset(cur_CardS_Status[slot], 0, sizeof(RIL_CardStatus_v6));
cur_CardS_Status[slot]->card_state = card_status->card_state;
cur_CardS_Status[slot]->cdma_subscription_app_index = card_status->cdma_subscription_app_index;
cur_CardS_Status[slot]->gsm_umts_subscription_app_index = card_status->gsm_umts_subscription_app_index;
cur_CardS_Status[slot]->ims_subscription_app_index = card_status->ims_subscription_app_index;
cur_CardS_Status[slot]->num_applications = card_status->num_applications;
cur_CardS_Status[slot]->universal_pin_state = card_status->universal_pin_state;
RLOGD("[slot%d]updateCardStatusV6 card_state: %d, cdma_index: %d, gsm_index: %d, "
"ims_index: %d, num_applications: %d, universal_pin_state: %d",
slot,
cur_CardS_Status[slot]->card_state,
cur_CardS_Status[slot]->cdma_subscription_app_index,
cur_CardS_Status[slot]->gsm_umts_subscription_app_index,
cur_CardS_Status[slot]->ims_subscription_app_index,
cur_CardS_Status[slot]->num_applications,
cur_CardS_Status[slot]->universal_pin_state);
if(card_status)
{
for(int i = 0; i < card_status->num_applications; i++) {
cur_CardS_Status[slot]->applications[i].app_state = card_status->applications[i].app_state;
cur_CardS_Status[slot]->applications[i].app_type = card_status->applications[i].app_type;
cur_CardS_Status[slot]->applications[i].perso_substate = card_status->applications[i].perso_substate;
cur_CardS_Status[slot]->applications[i].pin1 = card_status->applications[i].pin1;
cur_CardS_Status[slot]->applications[i].pin1_replaced = card_status->applications[i].pin1_replaced;
cur_CardS_Status[slot]->applications[i].pin2 = card_status->applications[i].pin2;
cur_CardS_Status[slot]->applications[i].aid_ptr = strdup(card_status->applications[i].aid_ptr);
cur_CardS_Status[slot]->applications[i].app_label_ptr = strdup(card_status->applications[i].app_label_ptr);
}
} else {
RLOGD("[slot%d]updateCardStatusV6: sim card message is null", slot);
}
}
char* getAid(int slot)
{
char* aid = "";
int index = -1;
if(cur_CardS_Status[slot] != NULL){
if(Phone_utils::get_phone_type(slot) == Phone_utils::PHONE_TYPE_CDMA) {
index = cur_CardS_Status[slot]->cdma_subscription_app_index;
} else {
index = cur_CardS_Status[slot]->gsm_umts_subscription_app_index;
}
if(index >= 0 && index < cur_CardS_Status[slot]->num_applications) {
aid = cur_CardS_Status[slot]->applications[index].aid_ptr;
}
}
RLOGD("[slot%d] index: %d, getAid: %s", slot, index, aid);
return aid;
}
void update_reg_voice_service_state(int request, char *code, int slot, int32_t token)
{
if((reg_voice_service_state[slot] != atoi(code)) || ((token&RIL_TOKEN_MARK) == RIL_TOKEN_MARK)) {
reg_voice_service_state[slot] = atoi(code);
regCodeToServiceState(request, atoi(code), slot);
}
}
void update_reg_voice_radio_tech(int request, int code, int slot, int32_t token) {
if((reg_voice_radio_tech[slot] != code) || ((token&RIL_TOKEN_MARK) == RIL_TOKEN_MARK)){
reg_voice_radio_tech[slot] = code;
regCodeToRadioTechnology(request, code, slot);
}
}
void update_reg_data_service_state(int request, char *code,int slot, int32_t token)
{
if((reg_data_service_state[slot] != atoi(code)) || ((token&RIL_TOKEN_MARK) == RIL_TOKEN_MARK)) {
reg_data_service_state[slot] = atoi(code);
regCodeToServiceState(request, atoi(code), slot);
/*Warren change for SZZT 2021//11/14 start*/
int status = regCodeToServiceState(request, atoi(code), slot);
current_data_reg = status;
/*Warren change for SZZT 2021//11/14 end*/
}
}
void update_reg_data_radio_tech(int request, int code, int slot, int32_t token){
if((reg_data_radio_tech[slot] != code) || ((token&RIL_TOKEN_MARK) == RIL_TOKEN_MARK)) {
reg_data_radio_tech[slot] = code;
regCodeToRadioTechnology(request, code, slot);
}
}
void registerRadioOn(RfDesenseTxTest* rf){
if(!m_RfDesense) {
m_RfDesense = rf;
}
}
void unregisterRadioOn() {
if(m_RfDesense) {
m_RfDesense == NULL;
}
}
void registerRadioOffOrNotAvailable(RfDesenseTxTest* rf){
if(!m_RfDesense) {
m_RfDesense = rf;
}
}
void unregisterRadioOffOrNotAvailable() {
if(m_RfDesense) {
m_RfDesense == NULL;
}
}
void registerOnUnsolOemHookRaw(RfDesenseTxTest* rf){
if(!m_RfDesense) {
m_RfDesense = rf;
}
}
void unregisterOnUnsolOemHookRaw(){
if(m_RfDesense) {
m_RfDesense == NULL;
}
}
void register_response_oem_hook_raw(RfDesenseTxTest* rf){
if(!m_RfDesense) {
m_RfDesense = rf;
}
}
void unregister_response_oem_hook_raw(){
if(m_RfDesense) {
m_RfDesense == NULL;
}
}
void updateRadioStatus(int newValue ,RIL_SOCKET_ID soc_id)
{
RLOGD("updateRadioStatus oldState: %d, newState: %d", radio_status[soc_id], newValue);
bool newOn = (newValue == RADIO_STATE_ON);
bool oldOn = (radio_status[soc_id] == RADIO_STATE_ON);
bool newAvaiable = (newValue != RADIO_STATE_UNAVAILABLE);
bool oldAvaiable = (radio_status[soc_id] != RADIO_STATE_UNAVAILABLE);
if (newOn && !oldOn) {
RLOGD("RadioStateOn");
//printf("[SIM%d] radio on\n",soc_id +1);
if(m_RfDesense){
m_RfDesense->emRadioStateOn();
}
}
if ((!newOn || !newAvaiable) && !((!oldOn || !oldAvaiable))) {
RLOGD("RadioStateOfforNotAvailable");
//printf("[SIM%d] radio off or not available\n",soc_id +1);
if(m_RfDesense){
m_RfDesense->emRadioStateOfforNotAvailable();
}
}
if(newValue != radio_status[soc_id]) {
radio_status[soc_id] = newValue;
}
}
bool isRadioOn(RIL_SOCKET_ID soc_id)
{
return radio_status[soc_id] == RADIO_STATE_ON;
}
bool isRadioAvailable(RIL_SOCKET_ID soc_id)
{
return radio_status[soc_id] != RADIO_STATE_UNAVAILABLE;
}
static int regCodeToServiceState(int request,int code, int slot)
{
RLOGD("[slot%d]regCodeToServiceState %d, request: %s",slot, code, android::requestToString(request));
switch (code)
{
case 0:
case 2: // 2 is "searching"
case 3: // 3 is "registration denied"
case 4: // 4 is "unknown" no vaild in current baseband
case 10:// same as 0, but indicates that emergency call is possible.
case 12:// same as 2, but indicates that emergency call is possible.
case 13:// same as 3, but indicates that emergency call is possible.
case 14:// same as 4, but indicates that emergency call is possible.
{
if(request == RIL_REQUEST_VOICE_REGISTRATION_STATE) {
printf("[QUERY][VOICE REG_STATUS][SIM%d] The current service state is OUT OF SERVICE\n", slot);
} else {
printf("[QUERY][DATA REG_STATUS][SIM%d] The current service state is OUT OF SERVICE\n", slot);
}
return STATE_OUT_OF_SERVICE;
}
case 1:
case 5:
{
if(request == RIL_REQUEST_VOICE_REGISTRATION_STATE) {
printf("[QUERY][VOICE REG_STATUS][SIM%d] The current service state is IN SERVICE\n", slot);
} else {
printf("[QUERY][DATA REG_STATUS][SIM%d] The current service state is IN SERVICE\n", slot);
}
return STATE_IN_SERVICE;
}
default:
{
if(request == RIL_REQUEST_VOICE_REGISTRATION_STATE) {
printf("[QUERY][VOICE REG_STATUS][SIM%d] Unexpected service state %d\n", slot, code);
} else {
printf("[QUERY][DATA REG_STATUS][SIM%d] Unexpected service state %d\n", slot, code);
}
RLOGW("[SIM%d]regCodeToServiceState: unexpected service state %d", slot, code);
return STATE_OUT_OF_SERVICE;
}
}
}
static int regCodeToRadioTechnology(int request, int code, int slot) {
RLOGD("[slot%d]regCodeToRadioTechnology %d, request: %s",slot, code, android::requestToString(request));
switch(code) {
case RADIO_TECH_LTE:
{
if(request == RIL_REQUEST_VOICE_REGISTRATION_STATE) {
printf("[QUERY][VOICE REG_STATUS][SIM%d] The registered radio technology is 4G\n", slot);
} else {
printf("[QUERY][DATA REG_STATUS][SIM%d] The registered radio technology is 4G\n", slot);
}
break;
}
case RADIO_TECH_GSM:
case RADIO_TECH_GPRS:
case RADIO_TECH_EDGE:
case RADIO_TECH_IS95A:
case RADIO_TECH_IS95B:
case RADIO_TECH_1xRTT:
{
if(request == RIL_REQUEST_VOICE_REGISTRATION_STATE) {
printf("[QUERY][VOICE REG_STATUS][SIM%d] The registered radio technology is 2G\n", slot);
} else {
printf("[QUERY][DATA REG_STATUS][SIM%d] The registered radio technology is 2G\n", slot);
}
break;
}
case RADIO_TECH_UMTS:
case RADIO_TECH_HSDPA:
case RADIO_TECH_HSUPA:
case RADIO_TECH_HSPA:
case RADIO_TECH_EHRPD:
case RADIO_TECH_HSPAP:
case RADIO_TECH_TD_SCDMA:
case RADIO_TECH_EVDO_0:
case RADIO_TECH_EVDO_A:
case RADIO_TECH_EVDO_B:
{
if(request == RIL_REQUEST_VOICE_REGISTRATION_STATE) {
printf("[QUERY][VOICE REG_STATUS][SIM%d] The registered radio technology is 3G\n", slot);
} else {
printf("[QUERY][DATA REG_STATUS][SIM%d] The registered radio technology is 3G\n", slot);
}
break;
}
#ifdef TELEMATIC_5G_SUPPORT
case RADIO_TECH_NR://5G
{
if(request == RIL_REQUEST_VOICE_REGISTRATION_STATE) {
printf("[QUERY][VOICE REG_STATUS][SIM%d] The registered radio technology is 5G\n", slot);
} else {
printf("[QUERY][DATA REG_STATUS][SIM%d] The registered radio technology is 5G\n", slot);
}
break;
}
#endif
case RADIO_TECH_UNKNOWN:
{
if(request == RIL_REQUEST_VOICE_REGISTRATION_STATE) {
printf("[QUERY][VOICE REG_STATUS][SIM%d] The registered radio technology is unknown\n", slot);
} else {
printf("[QUERY][DATA REG_STATUS][SIM%d] The registered radio technology is unknown\n", slot);
}
break;
}
default:
{
if(request == RIL_REQUEST_VOICE_REGISTRATION_STATE) {
printf("[QUERY][VOICE REG_STATUS][SIM%d] %d is unexpected value\n",slot, code);
} else {
printf("[QUERY][DATA REG_STATUS][SIM%d] %d is unexpected value\n",slot, code);
}
}
}
return 0;
}
int get_reg_data_radio_tech(int slot) {
return reg_data_radio_tech[slot];
}
int get_reg_voice_radio_tech(int slot) {
return reg_voice_radio_tech[slot];
}
#ifdef ECALL_SUPPORT
void ConvertMsd(const char *msdChar, unsigned char *msd) {
unsigned int n, x;
for (n = 0; n < MSD_MAX_LENGTH; n++) {
if (sscanf(&msdChar[n<<1], "%2x", &x) == 1) {
msd[n] = x;
} else {
RLOGE("invalid MSD characters");
break;
}
}
}
#endif /*ECALL_SUPPORT*/
bool isFinalResponseErrorEx(char* str) {
AtLine atline(str, NULL);
return (atline.isFinalResponseErrorEx(0) == 1 ? true : false);
}
int get_atci_sim(){
return utils::mtk_property_get_int32(ATCI_SIM, 0);
}
static char *findNextChar(char *p, char c, int length)
{
char *ptr = p;
int i = 0;
while (i++ < length)
{
if (*ptr++ == c)
return ptr;
}
return NULL;
}
static int getGMTval(char *pdata)
{
char *ptr;
ptr = findNextChar(pdata, '+', strlen(pdata));
if (ptr == NULL)
{
ptr = findNextChar(pdata, '-', strlen(pdata));
if (ptr == NULL)
{
return 0;
}
}
return atoi(ptr);
}
static void adjustGMT2LocalTime(struct tm *src, int dGMTval)
{
time_t t1, t2;
struct tm * ptm;
char buf[255];
int dShiftSec;
dShiftSec = dGMTval * 15 * 60;
t1 = mktime(src);
t2 = (time_t)(t1 + dShiftSec);
ptm = gmtime(&t2);
memcpy(src, ptm, sizeof(struct tm));
}
void updateSystemTime(const void *data, int datalen)
{
char strTime[32];
struct tm tm;
time_t t;
int dGMTval;
char modem_sync_enable[24] = "";
if (data == NULL || datalen <= 0)
return;
memset(strTime, 0, sizeof(strTime));
strcat(strTime, "20");
strcat(strTime, (const char *)data);
dGMTval = getGMTval(strTime);
memset(&tm, 0, sizeof(struct tm));
strptime(strTime, "%Y/%m/%d,%H:%M:%S", &tm);
//adjustGMT2LocalTime(&tm, dGMTval);
t = mktime(&tm);
lynq_get_value("lynq_uci", "lynq_sync_time", "lynq_modem_sync_time_enable" , modem_sync_enable);
if(!atoi(modem_sync_enable))
return ;
stime(&t);
system("hwclock -w -f /dev/rtc0");
return;
}
void notifyDataSignal() {
RLOGE("notifyDataSignal()");
pthread_mutex_lock(&s_DataMutex);
pthread_cond_broadcast(&s_DataCond);
pthread_mutex_unlock(&s_DataMutex);
}
bool mtkItTest(const char* data) {
std::string str("");
str.append(data);
RLOGD("%s, data: %s", __FUNCTION__, str.c_str());
std::vector<std::string> all;
RequestInfo* pRI = NULL;
utils::tokenize(str, ',', all);
if(all[0] != std::string("TEST")) {
return false;
}
android::Parcel p;
size_t pos = p.dataPosition();
for(int i = 1 ; i < all.size(); i++) {
std::string str = all[i];
RLOGD("%s, all[%d]: %s", __FUNCTION__, i, str.c_str());
std::vector<std::string> items;
utils::tokenize(str, '=', items);
if(items.size() == 2) {
if(items[0] == std::string("INT")) {
int para = std::stoi(items[1]);
p.writeInt32(para);
} else if(items[0] == std::string("STR")) {
writeStringToParcel(p, items[1].c_str());
} else if(items[0] == std::string("REQ")) {
int request = std::stoi(items[1]);
// For loop, free before reassign to avoid memory leak
if (pRI != NULL) {
free(pRI);
}
pRI = creatRILInfoAndInit(request, UDP, (RIL_SOCKET_ID) ((0)));
}
} else {
RLOGD("%s, too many \"=\"");
}
}
if(pRI && pRI->pCI) {
p.setDataPosition(pos);
pRI->pCI->dispatchFunction(p, pRI);
}
// Free to avoid memory leak
if(pRI != NULL) {
free(pRI);
pRI = NULL;
}
return true;
}
int lynqSocketSendto(int fd,struct sockaddr *dest_addr,int addr_len,char msg[])
{
int ret = 0;
ret = sendto(fd,msg,strlen(msg),0,dest_addr,addr_len);
if(ret>0)
{
RLOGD("[lynqSocketSendto] send msg success!!!");
return 0;
}
else
{
RLOGD("[lynqSocketSendto] send msg fail!!!");
return -1;
}
}
void lynq_exit()
{
ril_deinit_mem();
#ifdef LED_SUPPORT
mbtk_netled_deinit();
#endif
}
#ifdef LED_SUPPORT
bool ril_get_if_insert_simcard()
{
int slot_id=get_default_sim_voice();
if(slot_id==0 || slot_id ==1)
{
if(cur_CardS_Status[slot_id]!=NULL)
{
return cur_CardS_Status[slot_id]->card_state == RIL_CARDSTATE_PRESENT;
}
}
return false;
}
bool ril_get_if_3gpp_reg_success()
{
int slot_id=get_default_sim_voice();
if(slot_id==0 || slot_id ==1)
{
return reg_voice_service_state[slot_id] ==1;
}
return false;
}
#endif
/*hq add for key info output 2022/03/01 begin*/
// void lynq_output_LINFO_all()
// {
// int slot,startSlot=0,slotNum=SIM_COUNT;
// if(default_sim_voice==default_sim_data && default_sim_voice==default_sim_sms){
// startSlot=default_sim_voice;
// slotNum=1;
// }
// lynq_output_info("+LINFO: Report switch when key information changed is set: %d\n",lynq_output_LINFO_enable);
// lynq_output_info("+LINFO: Default voice SIM card is set : [SIM%d]\n", default_sim_voice+1);
// lynq_output_info("+LINFO: Default data SIM card is set : [SIM%d]\n", default_sim_data+1);
// lynq_output_info("+LINFO: Default sms SIM card is set : [SIM%d]\n", default_sim_sms+1);
// for(slot=startSlot;slot<startSlot+slotNum;slot++){
// lynq_output_info("+LINFO: [SIM%d] Card State is %s\n",slot+1,cardStateToString((cur_CardS_Status[slot]!=NULL ? cur_CardS_Status[slot]->card_state:UNKOWN_VALUE)));
// lynq_output_info("+LINFO: [SIM%d] Preferred network_type: is %s\n", slot+1, preferredNetworkTypeToString(preferred_network_type[slot]));
// lynq_output_info("+LINFO: [SIM%d] Voice Registration State is %s\n",slot+1,serviceStateToString(regCodeToServiceState(reg_voice_service_state[slot])));
// lynq_output_info("+LINFO: [SIM%d] Voice Radio Access Network is %s\n",slot+1,RadioNwToString(regCodeToRadioTechnology(reg_voice_radio_tech[slot])));
// lynq_output_info("+LINFO: [SIM%d] Data Registration State is %s\n",slot+1,serviceStateToString(regCodeToServiceState(reg_data_service_state[slot])));
// lynq_output_info("+LINFO: [SIM%d] Data Radio Access Network is %s\n",slot+1,RadioNwToString(regCodeToRadioTechnology(reg_data_radio_tech[slot])));
// }
// return;
// }
// void lynq_output_LINFO(const char* format,...)
// {
// char buf[1024] = {0};
// int n;
// char ebuf[1024] = {0};
// if(lynq_output_LINFO_enable)
// {
// va_list args;
// va_start(args, format);
// vsnprintf(buf, sizeof(buf), format, args);
// va_end(args);
// printf("hq %s",buf);
// n=snprintf(ebuf,sizeof(ebuf),"+LINFO: %s", buf);
// n=write(ttyGS3_fd, ebuf, strlen(ebuf));
// if(n < 0)
// {
// perror("lynq resp write:");
// }
// }
// return;
// }
// void lynq_output_info(const char* format,...)
// {
// char buf[1024] = {0};
// int n;
// va_list args;
// va_start(args, format);
// vsnprintf(buf, sizeof(buf), format, args);
// va_end(args);
// n=write(ttyGS3_fd, buf, strlen(buf));
// if(n < 0)
// {
// perror("lynq resp write:");
// }
// return;
// }
/*hq add for key info output 2022/03/01 end*/