| /*------------------------------------------------------------ |
| (C) Copyright [2006-2014] Marvell International Ltd. |
| All Rights Reserved |
| ------------------------------------------------------------*/ |
| #include "XmlParser.h" |
| |
| ////////////////////////////////////////////////////////////////////// |
| // Defines |
| ////////////////////////////////////////////////////////////////////// |
| |
| ////////////////////////////////////////////////////////////////////// |
| // Local Prototypes |
| ////////////////////////////////////////////////////////////////////// |
| #if CONFIG_LIBXML2 |
| void parse_ex_apn(xmlTextReaderPtr reader,Mnc_Apn *get_apn); |
| void parse_apn(xmlTextReaderPtr reader, Mnc_Apn *get_apn); |
| int find_matched_apn(xmlTextReaderPtr reader,Mnc_Apn *get_apn); |
| void parse_ex_params(xmlTextReaderPtr reader,Extra_Apn_Info *ex_info); |
| static void remove_entry(xmlNodePtr cur,char *mcc,char *mnc,char *carrier); |
| static xmlDocPtr openXmlFile(char *docname) ; |
| static void closeXmlFile(xmlDocPtr xmlFilePtr); |
| static xmlNodePtr getXmlRoot(xmlDocPtr xmlFilePtr); |
| static xmlDocPtr createXmlFile(char *docname, char *root_name); |
| static int saveXmlFile(char *docname, xmlDocPtr xmlFilePtr); |
| #endif |
| |
| #if CONFIG_LIBMXML |
| void parse_ex_apn(mxml_node_t *node, Mnc_Apn *get_apn); |
| void parse_apn(mxml_node_t *node, Mnc_Apn *get_apn); |
| void parse_ex_params(mxml_node_t *node, Extra_Apn_Info *ex_info); |
| |
| #endif |
| |
| ////////////////////////////////////////////////////////////////////// |
| // Global Variables |
| ////////////////////////////////////////////////////////////////////// |
| |
| extern Mnc_Apn *IMSI_APN; |
| |
| apn_data apn_params_str[] = { |
| {APN_PARAM_CARRIER,"carrier"}, |
| {APN_PARAM_MCC,"mcc"}, |
| {APN_PARAM_MNC,"mnc"}, |
| {APN_PARAM_APN,"apn"}, |
| {APN_PARAM_USER,"user"}, |
| {APN_PARAM_SERVER,"server"}, |
| {APN_PARAM_PROXY,"proxy"}, |
| {APN_PARAM_PORT,"port"}, |
| {APN_PARAM_PASSWORD,"password"}, |
| {APN_PARAM_MMSC,"mmsc"}, |
| {APN_PARAM_MMSPROXY,"mmsproxy"}, |
| {APN_PARAM_MMSPORT,"mmsport"}, |
| {APN_PARAM_AUTHTYPE,"authtype"}, |
| {APN_PARAM_TYPE,"type"}, |
| {APN_PARAM_PROTOCOL,"protocol"}, |
| {APN_PARAM_PCO,"pco"}, |
| {APN_PARAM_VENDORSPECIFIC,"vendorspecific"}, |
| {APN_PARAM_ROAMINGPROTOCOL,"roaming_protocol"}, |
| {APN_PARAM_BEARER,"bearer"}, |
| {APN_PARAM_LAST,"last"} |
| }; |
| |
| extra_apn_data extra_apn_params_str[] = { |
| {EXTRA_APN_PARAM_AUTOCONNECT,"autoconnect"}, |
| {EXTRA_APN_PARAM_ALWAYSON,"always_on"}, |
| {EXTRA_APN_PARAM_LTEDEFAULT,"lte_default"}, |
| {EXTRA_APN_PARAM_CONFIGONLY,"config_only"}, |
| {EXTRA_APN_PARAM_TETHERABLE,"tetherable"}, |
| {EXTRA_APN_PARAM_ISHOST,"is_host"}, |
| {EXTRA_APN_PARAM_DATAONROAMING,"data_on_roaming"}, |
| {EXTRA_APN_PARAM_MTU,"mtu"}, |
| {EXTRA_APN_PARAM_LAST,"last"} |
| }; |
| ////////////////////////////////////////////////////////////////////// |
| // Functions implementations |
| ////////////////////////////////////////////////////////////////////// |
| |
| |
| /*========================== XML API ====================================*/ |
| |
| |
| #if CONFIG_LIBXML2 |
| /** |
| * remove a given entry {mcc,mnc,carrier} from xml file |
| * |
| * @param cur xml file root node |
| * @param mcc |
| * @param mnc |
| * @param carrier PDP carrier |
| */ |
| static void remove_entry(xmlNodePtr cur,char *mcc,char *mnc,char *carrier) |
| { |
| xmlNodePtr tempPtr,nodePtr = NULL; |
| xmlChar *mcc_p; |
| xmlChar *mnc_p; |
| xmlChar *carrier_p; |
| |
| if(cur == NULL) { |
| CM_Log(remove_entry, "XML parser: xmlCurNodePtr = NULL!!!"); |
| } else { |
| // Get next node, and start walking the XML tree |
| nodePtr = cur->children; |
| while (nodePtr != NULL) |
| { |
| if ((!xmlStrcmp(nodePtr->name, (const xmlChar *)"apn"))) { |
| |
| mcc_p = xmlGetProp(nodePtr, (const xmlChar *)"mcc"); |
| mnc_p = xmlGetProp(nodePtr, (const xmlChar *)"mnc"); |
| carrier_p = xmlGetProp(nodePtr, (const xmlChar *)"carrier"); |
| if (!xmlStrcmp(mcc_p, BAD_CAST mcc) && !xmlStrcmp(mnc_p, BAD_CAST mnc) && |
| !xmlStrcmp(carrier_p, BAD_CAST carrier)){ |
| /*match found - now delete it*/ |
| tempPtr = nodePtr; |
| nodePtr = nodePtr->next; |
| |
| /*delete the node*/ |
| xmlUnlinkNode(tempPtr); |
| xmlFreeNode(tempPtr); |
| |
| xmlFree(mcc_p); |
| xmlFree(mnc_p); |
| xmlFree(carrier_p); |
| continue; |
| } |
| } |
| //Get next node |
| nodePtr = nodePtr->next; |
| } |
| } |
| |
| return; |
| } |
| |
| |
| /******************************************************** |
| * Function: openXmlFile |
| * |
| * Input: char *docname - The XML file we want to open for parsing |
| * |
| * Description: Open the main XML file, and calls the parsing algorithm |
| */ |
| static xmlDocPtr openXmlFile(char *docname) |
| { |
| xmlDocPtr xmlFilePtr = xmlParseFile(docname); |
| |
| if (xmlFilePtr == NULL ) |
| { |
| CM_Log(openXmlFile, "openXmlFile - Error: Could not open XML file - %s !", docname); |
| } |
| |
| return xmlFilePtr; |
| } |
| |
| |
| /** |
| * return the root node of the xml file |
| * |
| * @param xmlFilePtr pointer of the xml file |
| * |
| * @return root node |
| */ |
| static xmlNodePtr getXmlRoot(xmlDocPtr xmlFilePtr) |
| { |
| xmlNodePtr root = xmlDocGetRootElement(xmlFilePtr); |
| |
| if (root != NULL){ |
| if (xmlStrcmp(root->name, (const xmlChar *) EXTRA_XML_ROOT_COMPONENT)) { |
| return NULL; |
| } |
| } |
| |
| return root; |
| } |
| |
| |
| /******************************************************** |
| * Function: createXmlFile |
| * |
| * Input: char *docname - The XML file we want to create |
| * |
| * Description: Create XML file with root element |
| */ |
| static xmlDocPtr createXmlFile(char *docname, char *root_name) |
| { |
| xmlNodePtr root; |
| xmlDocPtr xmlFilePtr = xmlNewDoc((const xmlChar *)"1.0"); |
| |
| if (xmlFilePtr == NULL ) { |
| CM_Log(createXmlFile, "createXmlFile - Could not create XML file - %s !", docname); |
| return FALSE; |
| } |
| |
| root = xmlNewNode(NULL, (const xmlChar *) root_name); |
| if (root == NULL) |
| { |
| CM_Log(createXmlFile1, "createXmlFile - Could not create new node - %s !", root_name); |
| xmlFreeDoc(xmlFilePtr); |
| return NULL; |
| } |
| |
| xmlDocSetRootElement(xmlFilePtr, root); |
| |
| if (saveXmlFile(docname, xmlFilePtr) == -1) |
| { |
| CM_Log(createXmlFile2, "createXmlFile - Could not save XML file - %s !", docname); |
| xmlFreeDoc(xmlFilePtr); |
| return NULL; |
| } |
| return xmlFilePtr; |
| } |
| |
| |
| /******************************************************** |
| * Function: saveXmlFile |
| * |
| * Description: Save the current XML Document to file |
| */ |
| static int saveXmlFile(char *docname, xmlDocPtr xmlFilePtr) |
| { |
| xmlKeepBlanksDefault(0); |
| xmlIndentTreeOutput = 1; |
| return xmlSaveFormatFileEnc(docname, xmlFilePtr, "UTF-8", 1); |
| } |
| |
| |
| /******************************************************** |
| * Function: closeXmlFile |
| * |
| * Description: Closes the current XML File |
| */ |
| static void closeXmlFile(xmlDocPtr xmlFilePtr) |
| { |
| if (xmlFilePtr != NULL) |
| { |
| xmlFreeDoc(xmlFilePtr); |
| } |
| else |
| { |
| CM_Log(closeXmlFile, "closeXmlFile - Error: Could not close XML file!"); |
| } |
| |
| return; |
| } |
| |
| |
| /** |
| * wrapper function: |
| * copy the given APN information struct to our database files |
| * |
| * @param ptr_apn pointer to APN information struct |
| * @param mcc |
| * @param mnc |
| * @param carrier PDP carrier |
| * |
| * @return 1 - success |
| * 0 - failed to set |
| */ |
| int set_params(Apn_Info *ptr_apn,char *mcc ,char *mnc ,char *carrier ) |
| { |
| int rc = 1; |
| char my_mcc[4]; |
| char my_mnc[4]; |
| |
| if (mcc == NULL || mnc == NULL) { |
| /* use mcc mnc from sim */ |
| strcpy(my_mcc, IMSI_APN->mcc); |
| strcpy(my_mnc, IMSI_APN->mnc); |
| }else{ |
| strcpy(my_mcc, mcc); |
| strcpy(my_mnc, mnc); |
| } |
| |
| /*set the overide params in the database*/ |
| rc &= set_additional_params(ptr_apn,my_mcc,my_mnc,carrier,1); |
| |
| /*set the extra params in the database*/ |
| rc &= set_additional_params(ptr_apn,my_mcc,my_mnc,carrier,0); |
| |
| /* return 1 for success */ |
| return rc; |
| } |
| |
| |
| /** |
| * copy the given APN information struct to our overide database |
| * |
| * @param node apn node containing the new information |
| * @param ptr_apn pointer to APN information struct |
| * @param mcc |
| * @param mnc |
| * @param carrier PDP carrier |
| */ |
| void set_overide_props(xmlNodePtr node,Apn_Info *ptr_apn,char *mcc,char *mnc,char *carrier) |
| { |
| xmlNewProp(node, BAD_CAST "carrier", BAD_CAST carrier); |
| xmlNewProp(node, BAD_CAST "mcc", BAD_CAST mcc); |
| xmlNewProp(node, BAD_CAST "mnc", BAD_CAST mnc); |
| |
| if ((strlen(ptr_apn->type))>0) { |
| xmlNewProp(node, BAD_CAST "type", BAD_CAST ptr_apn->type); |
| } |
| if ((strlen(ptr_apn->apn))>0) { |
| xmlNewProp(node, BAD_CAST "apn", BAD_CAST ptr_apn->apn); |
| } |
| if ((strlen(ptr_apn->protocol))>0) { |
| xmlNewProp(node, BAD_CAST "protocol", BAD_CAST ptr_apn->protocol); |
| } |
| if ((strlen(ptr_apn->usrname))>0) { |
| xmlNewProp(node, BAD_CAST "usrname", BAD_CAST ptr_apn->usrname); |
| } |
| if ((strlen(ptr_apn->paswd))>0) { |
| xmlNewProp(node, BAD_CAST "paswd", BAD_CAST ptr_apn->paswd); |
| } |
| if ((strlen(ptr_apn->server))>0) { |
| xmlNewProp(node, BAD_CAST "server", BAD_CAST ptr_apn->server); |
| } |
| if ((strlen(ptr_apn->proxy))>0) { |
| xmlNewProp(node, BAD_CAST "proxy", BAD_CAST ptr_apn->proxy); |
| } |
| if ((strlen(ptr_apn->port))>0) { |
| xmlNewProp(node, BAD_CAST "port", BAD_CAST ptr_apn->port); |
| } |
| if ((strlen(ptr_apn->mmsproxy))>0) { |
| xmlNewProp(node, BAD_CAST "mmsproxy", BAD_CAST ptr_apn->mmsproxy); |
| } |
| if ((strlen(ptr_apn->mmsport))>0) { |
| xmlNewProp(node, BAD_CAST "mmsport", BAD_CAST ptr_apn->mmsport); |
| } |
| if ((strlen(ptr_apn->mmsc))>0) { |
| xmlNewProp(node, BAD_CAST "mmsc", BAD_CAST ptr_apn->mmsc); |
| } |
| if ((strlen(ptr_apn->authtype))>0) { |
| xmlNewProp(node, BAD_CAST "authtype", BAD_CAST ptr_apn->authtype); |
| } |
| if ((strlen(ptr_apn->pco))>0) { |
| xmlNewProp(node, BAD_CAST "pco", BAD_CAST ptr_apn->pco); |
| } |
| if ((strlen(ptr_apn->vendorSpecific))>0) { |
| xmlNewProp(node, BAD_CAST "vendorspecific", BAD_CAST ptr_apn->vendorSpecific); |
| } |
| if ((strlen(ptr_apn->roamingProtocol))>0) { |
| xmlNewProp(node, BAD_CAST "roaming_protocol", BAD_CAST ptr_apn->roamingProtocol); |
| } |
| if ((strlen(ptr_apn->bearer))>0) { |
| xmlNewProp(node, BAD_CAST "bearer", BAD_CAST ptr_apn->bearer); |
| } |
| |
| return; |
| } |
| |
| |
| /** |
| * copy the given APN information struct to our extra database |
| * |
| * @param node apn node containing the new information |
| * @param ex_apn pointer to APN information struct |
| * @param mcc |
| * @param mnc |
| * @param carrier PDP carrier |
| */ |
| void set_extra_props(xmlNodePtr node,Extra_Apn_Info *ex_apn,char *mcc,char *mnc,char *carrier) |
| { |
| char buf[10] = {0}; |
| |
| xmlNewProp(node, BAD_CAST "carrier", BAD_CAST carrier); |
| xmlNewProp(node, BAD_CAST "mcc", BAD_CAST mcc); |
| xmlNewProp(node, BAD_CAST "mnc", BAD_CAST mnc); |
| |
| sprintf(buf,"%d",ex_apn->autoconnect); |
| xmlNewProp(node, BAD_CAST "autoconnect", BAD_CAST buf); |
| sprintf(buf,"%d",ex_apn->lte_default); |
| xmlNewProp(node, BAD_CAST "lte_default", BAD_CAST buf); |
| sprintf(buf,"%d",ex_apn->always_on); |
| xmlNewProp(node, BAD_CAST "always_on", BAD_CAST buf); |
| sprintf(buf,"%d",ex_apn->config_only); |
| xmlNewProp(node, BAD_CAST "config_only", BAD_CAST buf); |
| sprintf(buf,"%d",ex_apn->tetherable); |
| xmlNewProp(node, BAD_CAST "tetherable", BAD_CAST buf); |
| sprintf(buf,"%d",ex_apn->is_host); |
| xmlNewProp(node, BAD_CAST "is_host", BAD_CAST buf); |
| sprintf(buf,"%d",ex_apn->data_on_roaming); |
| xmlNewProp(node, BAD_CAST "data_on_roaming", BAD_CAST buf); |
| sprintf(buf,"%d",ex_apn->mtu); |
| xmlNewProp(node, BAD_CAST "mtu", BAD_CAST buf); |
| return; |
| } |
| |
| |
| /** |
| * check if file is existed |
| * |
| * @param fname filename - full path |
| * |
| * @return 1 - file exist |
| * 0 - file doesn't exist |
| */ |
| int is_file_existed(char *fname ) |
| { |
| if( access( fname, F_OK ) != -1 ) |
| /* file exists */ |
| return 1; |
| else{ |
| /* file NOT exists */ |
| if (errno == ENOENT) |
| return 0; |
| //other error that we didn't expect - why retun TRUE if file not exist???? |
| return 1; |
| } |
| } |
| |
| |
| /** |
| * remove apn entry from our database |
| * |
| * @param mcc |
| * @param mnc |
| * @param carrier PDP carrier |
| * @param option 0 - overide DB |
| * 1 - extra DB |
| * |
| * @return 1 - success |
| * 0 - failure |
| */ |
| int remove_apn(char *mcc ,char *mnc ,char *carrier, int option) { |
| xmlDocPtr xmlFilePtr = NULL; |
| xmlNodePtr root; |
| char fname[50] = {0}; |
| |
| if (option == 0) |
| strcpy(fname,APNS_OVERIDE_FILENAME); |
| else |
| strcpy(fname,APNS_EXTRA_FILENAME); |
| |
| xmlFilePtr = openXmlFile(fname); |
| if (xmlFilePtr == NULL) |
| return 0; |
| |
| root = getXmlRoot(xmlFilePtr); |
| if (root == NULL) |
| return 0; |
| |
| remove_entry(root,mcc,mnc,carrier); |
| |
| if (saveXmlFile(fname, xmlFilePtr) == -1) |
| { |
| CM_Log(remove_apn, "remove_apn - Error: Could not save XML file - %s !", fname); |
| xmlFreeDoc(xmlFilePtr); |
| return 0; |
| } |
| closeXmlFile(xmlFilePtr); |
| return 1; |
| } |
| |
| |
| /** |
| * copy the given APN information struct to our database files |
| * |
| * @param ptr_apn pointer to APN information struct |
| * @param mcc |
| * @param mnc |
| * @param carrier PDP carrier |
| * @param option 0 - copy to the overide xml |
| * 1 - copy to the extra xml |
| * |
| * @return 1 - success |
| * 0 - failed to set |
| */ |
| int set_additional_params(Apn_Info *ptr_apn,char *mcc ,char *mnc ,char *carrier,int option ){ |
| xmlDocPtr xmlFilePtr = NULL; |
| xmlNodePtr root; |
| xmlNodePtr node; |
| char fname[50] = {0}; |
| char *tmp_carrier = NULL; |
| Extra_Apn_Info *ex_apn = &(ptr_apn->Extra_params); |
| |
| CM_Log(set_additional_params, "set_additional_params: mcc=%s,mnc=%s,carrier=%s,option=%d", mcc, mnc, carrier, option); |
| if (option == 0) |
| strcpy(fname,APNS_OVERIDE_FILENAME); |
| else |
| strcpy(fname,APNS_EXTRA_FILENAME); |
| |
| /*check if the databse file is already existed*/ |
| if (is_file_existed(fname)){ |
| CM_Log(set_additional_params1, "set_additional_params - XML file - %s exist!", fname); |
| xmlFilePtr = openXmlFile(fname); |
| } |
| |
| if (xmlFilePtr == NULL) { |
| CM_Log(set_additional_params2, "set_additional_params - XML file - %s doesn't exist! create it!", fname); |
| xmlFilePtr = createXmlFile(fname,EXTRA_XML_ROOT_COMPONENT); |
| xmlFilePtr = openXmlFile(fname); |
| } |
| /*get root node*/ |
| root = getXmlRoot(xmlFilePtr); |
| if (root == NULL) |
| return 0; |
| |
| /*if this entry (mcc,mnc,carrier) already existed - need to remove*/ |
| remove_entry(root,mcc,mnc,carrier); |
| /*if the carrier has changed - need to remove if exist */ |
| if(strcmp(carrier, ptr_apn->carrier)) { |
| remove_entry(root,mcc,mnc,ptr_apn->carrier); |
| } |
| |
| if(!strcmp(ptr_apn->carrier, "")) |
| tmp_carrier = carrier; |
| else |
| tmp_carrier = ptr_apn->carrier; |
| |
| node=xmlNewChild(root, NULL, BAD_CAST "apn", NULL); |
| |
| if (option == 0) |
| set_overide_props(node,ptr_apn,mcc,mnc,tmp_carrier); |
| else |
| set_extra_props(node,ex_apn,mcc,mnc,tmp_carrier); |
| |
| if (saveXmlFile(fname, xmlFilePtr) == -1) |
| { |
| CM_Log(set_additional_params3, "set_additional_params - Error: Could not save XML file - %s !", fname); |
| xmlFreeDoc(xmlFilePtr); |
| return 0; |
| } |
| closeXmlFile(xmlFilePtr); |
| return 1; |
| } |
| #endif |
| |
| /** |
| * get default APN information from our database |
| * |
| * @param docname xml filename (database of the default params) |
| * @param ex_apn extra APN struct to fill |
| * |
| * @return 0 - no default params are found or error |
| * 1 - default params are found |
| */ |
| int get_default_params(char *docname,Extra_Apn_Info *ex_apn,const char *type) { |
| |
| #if CONFIG_LIBXML2 |
| xmlTextReaderPtr reader; |
| xmlChar *name; |
| #elif CONFIG_LIBMXML |
| mxml_node_t *root = NULL; |
| mxml_node_t *cur = NULL; |
| FILE *fp = NULL; |
| #endif |
| |
| int ret,j,i=0; |
| char *param[7] = {NULL}; |
| char *tok = NULL; |
| char *tmp_type = malloc(strlen(type)+1); |
| |
| strcpy(tmp_type, type); |
| while ((tok = strsep(&tmp_type, ",")) != NULL && i < 7) { |
| param[i] = tok; |
| i++; |
| } |
| free(tmp_type); |
| |
| #if CONFIG_LIBMXML |
| fp = fopen(docname, "r"); |
| if (fp == NULL) { |
| ret = -1; |
| goto end; |
| } |
| root = mxmlLoadFile(NULL, fp, MXML_OPAQUE_CALLBACK); |
| fclose(fp); |
| #endif |
| |
| for (j=0;j<i;j++) { |
| #if CONFIG_LIBXML2 |
| /*open the xml file*/ |
| reader = xmlNewTextReaderFilename(docname); |
| if (reader != NULL ) { |
| /*read the root node*/ |
| ret = xmlTextReaderRead(reader); |
| |
| while (ret == 1) { |
| name = xmlTextReaderName(reader); |
| /*search for default configuration for this PDP type*/ |
| if (!xmlStrcmp(name, (xmlChar*) param[j])){ |
| /*parse deafult apn params to struct*/ |
| parse_ex_params(reader,ex_apn); |
| xmlFreeTextReader(reader); |
| return 1; |
| } |
| /*read the next node*/ |
| ret = xmlTextReaderRead(reader); |
| } |
| /*EOF -no more nodes to read, ret should be 0*/ |
| xmlFreeTextReader(reader); |
| if (ret != 0) { |
| CM_Log(get_default_params, "%s : failed to parse\n", docname); |
| return 0; |
| } |
| } else { |
| CM_Log(get_default_params1, "Unable to open %s\n", docname); |
| return 0; |
| } |
| #elif CONFIG_LIBMXML |
| CM_Log(get_default_params, "%s: param[%d] %s\n", __func__, j, param[j]); |
| cur = mxmlFindElement(root, root, param[j], NULL, NULL, MXML_DESCEND); |
| if (cur == NULL) { |
| CM_Log(get_default_params604, "%s: can't find node %s\n", __func__, param[j]); |
| ret = -1; |
| goto end; |
| } |
| parse_ex_params(cur,ex_apn); |
| ret = 1; |
| end: |
| if (root) |
| mxmlDelete(root); |
| |
| return ret; |
| #endif |
| } |
| return 1; |
| } |
| |
| /** |
| * transforms given basic apn param string to its enum index |
| * |
| * @param str string of basic apn parameter |
| * |
| * @return enum index |
| */ |
| enum apn_params apn_param_str_to_enum(char *str) { |
| int i; |
| for (i=0;i<APN_PARAM_LAST;i++) { |
| if (!strcmp(str,apn_params_str[i].str)) { |
| return apn_params_str[i].entry; |
| } |
| } |
| return APN_PARAM_LAST; |
| } |
| |
| |
| /** |
| * transforms given extra apn param string to its enum index |
| * |
| * @param str string of extra apn parameter |
| * |
| * @return enum index |
| */ |
| enum extra_apn_params ex_apn_param_str_to_enum(char *str) { |
| int i; |
| for (i=0;i<EXTRA_APN_PARAM_LAST;i++) { |
| if (!strcmp(str,extra_apn_params_str[i].str)) { |
| return extra_apn_params_str[i].entry; |
| } |
| } |
| return EXTRA_APN_PARAM_LAST; |
| } |
| |
| |
| /** |
| * parse basic/overide apn information from the database, to our APN struct |
| * |
| * @param reader apn node in the extra file with {mcc,mnc} as in our basic struct |
| * @param get_apn struct contain APN information - mcc&mnc |
| */ |
| #if CONFIG_LIBXML2 |
| void parse_apn(xmlTextReaderPtr reader,Mnc_Apn *get_apn){ |
| xmlChar *temp; |
| #elif CONFIG_LIBMXML |
| void parse_apn(mxml_node_t *node, Mnc_Apn *get_apn){ |
| const xmlChar *temp; |
| #endif |
| int i; |
| char tmp_apn_param[APN_PARAM_LAST][MAX_STR_LEN] = {{0}}; |
| |
| Apn_Info *tmp_info = NULL; |
| |
| for (i=0; i<APN_PARAM_LAST; i++) { |
| #if CONFIG_LIBXML2 |
| temp = xmlTextReaderGetAttribute(reader,(const xmlChar *)apn_params_str[i].str); |
| #elif CONFIG_LIBMXML |
| temp = (const xmlChar * )mxmlElementGetAttr(node, apn_params_str[i].str); |
| #endif |
| |
| if (temp) { |
| if(apn_param_str_to_enum(apn_params_str[i].str) < APN_PARAM_LAST) { |
| //coverity[overrun-local:SUPPRESS] |
| strncpy(tmp_apn_param[apn_param_str_to_enum(apn_params_str[i].str)],(char *)temp,MAX_STR_LEN-1); |
| CM_Log(parse_apn681, "found attr:%d - name %s, value %s\n", i, apn_params_str[i].str, temp); |
| } else { |
| CM_Log(parse_apn686, "apn_param_str_to_enum overrun %s\n"); |
| } |
| #if CONFIG_LIBXML2 |
| xmlFree(temp); |
| #endif |
| } |
| } |
| |
| /* run to the end of the APN list and add new Apn_Info |
| or if APN carrier is already exist - override!*/ |
| for (i=0; i<MAX_APN_NUM; i++) { |
| tmp_info = &(get_apn->apn_info_list[i]); |
| if (tmp_info->basic_set == 0) { |
| tmp_info->basic_set = 1; |
| break; |
| } |
| |
| CM_Log(parse_apn697, "carrier %s\n", tmp_info->carrier); |
| if ((strlen(tmp_apn_param[APN_PARAM_CARRIER]) > 0) && |
| !strcmp(tmp_info->carrier, tmp_apn_param[APN_PARAM_CARRIER])) |
| break; |
| } |
| if (i == MAX_APN_NUM) //APN list is full |
| return; |
| |
| /*fill the APN info struct with the parsed values */ |
| if (strlen(tmp_apn_param[APN_PARAM_CARRIER]) > 0) { |
| strcpy(tmp_info->carrier,tmp_apn_param[APN_PARAM_CARRIER]); |
| CM_Log(parse_apn, "found APN:%d - %s\n", i, tmp_info->carrier); |
| } |
| |
| if (strlen(tmp_apn_param[APN_PARAM_APN]) > 0) { |
| strcpy(tmp_info->apn,tmp_apn_param[APN_PARAM_APN]); |
| strcpy(tmp_info->lte_apn,tmp_apn_param[APN_PARAM_APN]); |
| CM_Log(parse_apn, "found APN name:%d - %s\n", i, tmp_info->apn); |
| } |
| |
| if (strlen(tmp_apn_param[APN_PARAM_TYPE]) > 0) { |
| strcpy(tmp_info->type,tmp_apn_param[APN_PARAM_TYPE]); |
| } |
| |
| if (strlen(tmp_apn_param[APN_PARAM_USER]) > 0) { |
| strcpy(tmp_info->usrname,tmp_apn_param[APN_PARAM_USER]); |
| strcpy(tmp_info->lte_usrname,tmp_apn_param[APN_PARAM_USER]); |
| } |
| |
| if (strlen(tmp_apn_param[APN_PARAM_PASSWORD]) > 0) { |
| strcpy(tmp_info->paswd,tmp_apn_param[APN_PARAM_PASSWORD]); |
| strcpy(tmp_info->lte_paswd,tmp_apn_param[APN_PARAM_PASSWORD]); |
| } |
| |
| if (strlen(tmp_apn_param[APN_PARAM_SERVER]) > 0) { |
| strcpy(tmp_info->server,tmp_apn_param[APN_PARAM_SERVER]); |
| } |
| |
| if (strlen(tmp_apn_param[APN_PARAM_PROXY]) > 0) { |
| strcpy(tmp_info->proxy,tmp_apn_param[APN_PARAM_PROXY]); |
| } |
| |
| if (strlen(tmp_apn_param[APN_PARAM_PORT]) > 0) { |
| strcpy(tmp_info->port,tmp_apn_param[APN_PARAM_PORT]); |
| } |
| |
| if (strlen(tmp_apn_param[APN_PARAM_MMSPROXY]) > 0) { |
| strcpy(tmp_info->mmsproxy,tmp_apn_param[APN_PARAM_MMSPROXY]); |
| } |
| |
| if (strlen(tmp_apn_param[APN_PARAM_MMSPORT]) > 0) { |
| strcpy(tmp_info->mmsport,tmp_apn_param[APN_PARAM_MMSPORT]); |
| } |
| |
| if (strlen(tmp_apn_param[APN_PARAM_MMSC]) > 0) { |
| strcpy(tmp_info->mmsc,tmp_apn_param[APN_PARAM_MMSC]); |
| } |
| |
| if (strlen(tmp_apn_param[APN_PARAM_AUTHTYPE]) > 0) { |
| strcpy(tmp_info->authtype,tmp_apn_param[APN_PARAM_AUTHTYPE]); |
| strcpy(tmp_info->lte_authtype,tmp_apn_param[APN_PARAM_AUTHTYPE]); |
| } |
| |
| if (strlen(tmp_apn_param[APN_PARAM_PROTOCOL]) > 0) { |
| strcpy(tmp_info->protocol,tmp_apn_param[APN_PARAM_PROTOCOL]); |
| } |
| |
| if (strlen(tmp_apn_param[APN_PARAM_PCO]) > 0) { |
| strcpy(tmp_info->pco,tmp_apn_param[APN_PARAM_PCO]); |
| } |
| |
| if (strlen(tmp_apn_param[APN_PARAM_VENDORSPECIFIC]) > 0) { |
| strcpy(tmp_info->vendorSpecific,tmp_apn_param[APN_PARAM_VENDORSPECIFIC]); |
| } |
| |
| if (strlen(tmp_apn_param[APN_PARAM_ROAMINGPROTOCOL]) > 0) { |
| strcpy(tmp_info->roamingProtocol,tmp_apn_param[APN_PARAM_ROAMINGPROTOCOL]); |
| } |
| |
| if (strlen(tmp_apn_param[APN_PARAM_BEARER]) > 0) { |
| strcpy(tmp_info->bearer,tmp_apn_param[APN_PARAM_BEARER]); |
| } |
| |
| //set IPV4 as default |
| tmp_info->iptype=1; |
| |
| return; |
| } |
| |
| |
| /** |
| * assuming basic\overide information has already been parsed, |
| * parse extra apn information from the database, |
| * to our APN struct |
| * |
| * @param reader apn node in the extra file with {mcc,mnc} as in our basic struct |
| * @param get_apn struct contain APN information - mcc&mnc |
| */ |
| #if CONFIG_LIBXML2 |
| void parse_ex_apn(xmlTextReaderPtr reader,Mnc_Apn *get_apn){ |
| xmlChar *carrier; |
| #elif CONFIG_LIBMXML |
| void parse_ex_apn(mxml_node_t *node, Mnc_Apn *get_apn){ |
| const xmlChar *carrier; |
| #endif |
| Apn_Info *tmp_info; |
| int i; |
| |
| //APN type in the extra configuration file |
| #if CONFIG_LIBXML2 |
| carrier = xmlTextReaderGetAttribute(reader,(const xmlChar *)"carrier"); |
| #endif |
| |
| #if CONFIG_LIBMXML |
| carrier = (const xmlChar *)mxmlElementGetAttr(node, "carrier"); |
| #endif |
| |
| if (carrier == NULL) |
| return; |
| |
| /*run through APN list and check APN carrier match*/ |
| for (i=0; i<MAX_APN_NUM; i++) { |
| /*missing default params*/ |
| if (get_apn->apn_info_list[i].basic_set == 0) { |
| return; |
| } |
| tmp_info = &(get_apn->apn_info_list[i]); |
| #if CONFIG_LIBXML2 |
| if (!xmlStrcmp(carrier, (const xmlChar *)tmp_info->carrier)){ |
| /*APN carrier match - parse the extra parameters*/ |
| parse_ex_params(reader,&(tmp_info->Extra_params)); |
| } |
| #endif |
| |
| #if CONFIG_LIBMXML |
| CM_Log(parse_ex_apn834, "%s: carrier %s, apn_info_list[%d] carrier %s\n", __func__, carrier, i, tmp_info->carrier); |
| if (!strcmp((const char *)carrier, (const char *)tmp_info->carrier)){ |
| parse_ex_params(node,&(tmp_info->Extra_params)); |
| } |
| #endif |
| tmp_info->extra_set = 1; |
| } |
| #if CONFIG_LIBXML2 |
| xmlFree(carrier); |
| #endif |
| CM_Log(parse_ex_apn844, "%s: done\n", __func__); |
| return; |
| } |
| |
| |
| /** |
| * parse extra APN information to struct |
| * |
| * @param reader apn node in the extra/default file with {mcc,mnc} as in our basic struct |
| * @param ex_info extra APN information struct |
| */ |
| #if CONFIG_LIBXML2 |
| void parse_ex_params(xmlTextReaderPtr reader,Extra_Apn_Info *ex_info){ |
| xmlChar *temp; |
| #elif CONFIG_LIBMXML |
| void parse_ex_params(mxml_node_t *node, Extra_Apn_Info *ex_info){ |
| const xmlChar *temp; |
| #endif |
| int i; |
| char tmp_ex_apn_param[EXTRA_APN_PARAM_LAST][MAX_STR_LEN] = {{0}}; |
| |
| for (i=0; i<EXTRA_APN_PARAM_LAST; i++){ |
| /*search for specific extra param in the apn node*/ |
| #if CONFIG_LIBXML2 |
| temp = xmlTextReaderGetAttribute(reader,(const xmlChar *)extra_apn_params_str[i].str); |
| #elif CONFIG_LIBMXML |
| temp = (const xmlChar *)mxmlElementGetAttr(node, (const char*)extra_apn_params_str[i].str); |
| #endif |
| if (temp) { |
| /*extra param has been found, copy to a sorted struct*/ |
| if(ex_apn_param_str_to_enum(extra_apn_params_str[i].str) < EXTRA_APN_PARAM_LAST) { |
| //coverity[overrun-local:SUPPRESS] |
| strncpy(tmp_ex_apn_param[ex_apn_param_str_to_enum(extra_apn_params_str[i].str)],(char *)temp,MAX_STR_LEN-1); |
| CM_Log(parse_ex_params865, "%s: %s - %s\n", __func__, extra_apn_params_str[i].str, tmp_ex_apn_param[ex_apn_param_str_to_enum(extra_apn_params_str[i].str)]); |
| } else { |
| CM_Log(parse_ex_params882, "%s: tmp_ex_apn_param overrun\n", __func__); |
| } |
| #if CONFIG_LIBXML2 |
| xmlFree(temp); |
| #endif |
| } |
| } |
| |
| /*now all the extra apn params are in a sorted struct |
| fill the EXTRA APN info struct with the parsed values */ |
| |
| if (strlen(tmp_ex_apn_param[EXTRA_APN_PARAM_AUTOCONNECT]) > 0) { |
| ex_info->autoconnect = (int)(tmp_ex_apn_param[EXTRA_APN_PARAM_AUTOCONNECT][0]-'0'); |
| } |
| |
| if (strlen(tmp_ex_apn_param[EXTRA_APN_PARAM_ALWAYSON]) > 0) { |
| ex_info->always_on = (int)(tmp_ex_apn_param[EXTRA_APN_PARAM_ALWAYSON][0]-'0'); |
| } |
| |
| if (strlen(tmp_ex_apn_param[EXTRA_APN_PARAM_LTEDEFAULT]) > 0) { |
| ex_info->lte_default = (int)(tmp_ex_apn_param[EXTRA_APN_PARAM_LTEDEFAULT][0]-'0'); |
| } |
| |
| if (strlen(tmp_ex_apn_param[EXTRA_APN_PARAM_CONFIGONLY]) > 0) { |
| ex_info->config_only = (int)(tmp_ex_apn_param[EXTRA_APN_PARAM_CONFIGONLY][0]-'0'); |
| } |
| |
| if (strlen(tmp_ex_apn_param[EXTRA_APN_PARAM_TETHERABLE]) > 0) { |
| ex_info->tetherable = (int)(tmp_ex_apn_param[EXTRA_APN_PARAM_TETHERABLE][0]-'0'); |
| } |
| |
| if (strlen(tmp_ex_apn_param[EXTRA_APN_PARAM_ISHOST]) > 0) { |
| ex_info->is_host = (int)(tmp_ex_apn_param[EXTRA_APN_PARAM_ISHOST][0]-'0'); |
| } |
| |
| if (strlen(tmp_ex_apn_param[EXTRA_APN_PARAM_DATAONROAMING]) > 0) { |
| ex_info->data_on_roaming = (int)(tmp_ex_apn_param[EXTRA_APN_PARAM_DATAONROAMING][0]-'0'); |
| } |
| |
| if (strlen(tmp_ex_apn_param[EXTRA_APN_PARAM_MTU]) > 0) { |
| ex_info->mtu = atoi(tmp_ex_apn_param[EXTRA_APN_PARAM_MTU]); |
| } |
| |
| CM_Log(parse_ex_params908, "%s: done\n", __func__); |
| return; |
| } |
| |
| #if CONFIG_LIBXML2 |
| /** |
| * find APN node with a given mcc,mnc pair |
| * |
| * @param reader apn node to search |
| * @param get_apn struct contain APN information - mcc&mnc |
| * |
| * @return 0 - match not found |
| * 1 - match found |
| */ |
| int find_matched_apn(xmlTextReaderPtr reader,Mnc_Apn *get_apn){ |
| |
| xmlChar *mcc; |
| xmlChar *mnc; |
| |
| mcc = xmlTextReaderGetAttribute(reader,(const xmlChar *)"mcc"); |
| mnc = xmlTextReaderGetAttribute(reader,(const xmlChar *)"mnc"); |
| if ( (!xmlStrcmp(mcc, (const xmlChar *)get_apn->mcc)) && (!xmlStrcmp(mnc, (const xmlChar *)get_apn->mnc)) ){ |
| xmlFree(mcc); |
| xmlFree(mnc); |
| return 1; |
| }else{ |
| xmlFree(mcc); |
| xmlFree(mnc); |
| return 0; |
| } |
| } |
| #endif |
| |
| /** |
| * asumming mcc,mnc already received from sim. |
| * get APN information according to mcc && mnc we got in plmn from sim. |
| * search for matching APNS in our database |
| * |
| * @param docname xml filename (database) |
| * @param get_apn APN struct to fill, already containing mcc&mnc |
| * @param option 0 - get basic\overide APN information |
| * 1 - get extra APN information |
| * |
| * @return 0 - no match found for mcc&mnc pair in filename.xml |
| * 1 - match found for mcc&mnc pair in the filename.xml |
| */ |
| int get_apn_info_byMccMnc(char *docname,Mnc_Apn *get_apn,int option) { |
| #if CONFIG_LIBXML2 |
| xmlTextReaderPtr reader; |
| int ret,found = 0; |
| |
| reader = xmlNewTextReaderFilename(docname); |
| if (reader != NULL ) { |
| ret = xmlTextReaderRead(reader); |
| while (ret == 1) { |
| if (find_matched_apn(reader,get_apn)){ |
| found = 1; |
| if (option == 0) |
| parse_apn(reader,get_apn); |
| else |
| parse_ex_apn(reader,get_apn); |
| } |
| ret = xmlTextReaderRead(reader); |
| } |
| xmlFreeTextReader(reader); |
| if (ret != 0) { |
| CM_Log(get_apn_info_byMccMnc, "%s : failed to parse\n", docname); |
| return 0; |
| } |
| } else { |
| CM_Log(get_apn_info_byMccMnc1, "Unable to open %s\n", docname); |
| return 0; |
| } |
| return found; |
| |
| #elif CONFIG_LIBMXML |
| mxml_node_t *root = NULL; |
| mxml_node_t *cur = NULL; |
| mxml_node_t *node = NULL; |
| FILE *fp = NULL; |
| int found = 0; |
| const xmlChar *temp; |
| |
| fp = fopen(docname, "r"); |
| if (fp == NULL) { |
| goto end; |
| } |
| root = mxmlLoadFile(NULL, fp, MXML_OPAQUE_CALLBACK); |
| fclose(fp); |
| |
| CM_Log(get_apn_info_byMccMnc989, "%s : docname %s, root %x\n",__func__, docname, root); |
| node = root; |
| |
| while (1) |
| { |
| cur = mxmlFindElement(node, root, "apn", "mcc", get_apn->mcc, MXML_DESCEND); |
| if (cur == NULL) { |
| CM_Log(get_apn_info_byMccMnc994, "%s : find mcc=%s failed\n", __func__, get_apn->mcc); |
| goto end; |
| } |
| |
| cur = mxmlFindElement(cur->prev, root, "apn", "mnc", get_apn->mnc, MXML_DESCEND); |
| if (cur == NULL) { |
| CM_Log(get_apn_info_byMccMnc1000, "%s : find mnc=%s failed\n", __func__, get_apn->mnc); |
| goto end; |
| } |
| |
| CM_Log(get_apn_info_byMccMnc1013, "%s : find entry for{ mcc=%s, mnc=%s}\n", __func__, get_apn->mcc, get_apn->mnc); |
| temp = (const xmlChar * )mxmlElementGetAttr(cur, apn_params_str[APN_PARAM_MCC].str); |
| if (temp && strcmp((char *)temp, get_apn->mcc)) |
| { |
| /*parsed mcc not match */ |
| CM_Log(get_apn_info_byMccMnc1027, "%s : parsed mcc value %s, not matched, find next\n", __func__, temp); |
| node = cur->next; |
| continue; |
| } |
| found = 1; |
| if (option == 0) |
| parse_apn(cur, get_apn); |
| else |
| parse_ex_apn(cur, get_apn); |
| |
| node = cur->next; |
| } |
| |
| end: |
| |
| if (root) |
| mxmlDelete(root); |
| |
| CM_Log(get_apn_info_byMccMnc1028, "%s : found %d\n", __func__, found); |
| return found; |
| #endif |
| } |
| |
| |
| /** |
| * run over the apns list, |
| * and attach default params for each case there is no extra params |
| * |
| * @param mnc_data struct containing all the apns for given {mcc,mnc} |
| * @param default_params |
| * struct containing the default params |
| */ |
| void attachDefaultParams(Mnc_Apn* mnc_data) |
| { |
| int i,ret=0; |
| Apn_Info* apn_ptr; |
| Extra_Apn_Info default_params; |
| |
| for (i=0;i<MAX_APN_NUM;i++) { |
| apn_ptr = &(mnc_data->apn_info_list[i]); |
| memset(&default_params,0,sizeof(Extra_Apn_Info)); |
| |
| /*check if basic information is set*/ |
| if (apn_ptr->basic_set == 0) |
| return; |
| |
| /*check if extra information is set*/ |
| if (apn_ptr->extra_set == 1) |
| continue; |
| /*no extra information use default values*/ |
| |
| ret = get_default_params(APNS_DEFAULT_FILENAME,&default_params,apn_ptr->type); |
| if (ret==0){ |
| CM_Log(attachDefaultParams, "attachDefaultParams - Error: missing default configuration file!"); |
| return; |
| } |
| apn_ptr->Extra_params = default_params; |
| apn_ptr->extra_set = 1; |
| } |
| return; |
| } |
| |
| |
| /** |
| * fill APN's struct according to mcc && mnc. |
| * search for matching APNS in our database and fill the APN's struct |
| * |
| * @param mcc |
| * @param mnc |
| * @param mnc_data APN's struct to fill |
| */ |
| int fillApnInfo (char *mcc,char* mnc,Mnc_Apn *mnc_data){ |
| |
| int ret = 0; |
| |
| if (mcc == NULL || mnc == NULL) { |
| /* use mcc mnc from sim */ |
| strcpy(mnc_data->mcc, IMSI_APN->mcc); |
| strcpy(mnc_data->mnc, IMSI_APN->mnc); |
| }else{ |
| /*may match many mncs with mcc but has different mnc length*/ |
| strncpy(mnc_data->mcc, mcc, sizeof(mnc_data->mcc) - 1); |
| strncpy(mnc_data->mnc, mnc, sizeof(mnc_data->mnc) - 1); |
| } |
| |
| /* fill basic/overide APN information */ |
| ret |= get_apn_info_byMccMnc(APNS_FULL_FILENAME,mnc_data,0); |
| ret |= get_apn_info_byMccMnc(APNS_OVERIDE_FILENAME,mnc_data,0); |
| |
| if (ret == 0){ |
| CM_Log(fillApnInfo, "fillApnInfo - Error: {mcc=%s,mnc=%s} not found !", mcc, mnc); |
| return ret; |
| } |
| |
| /* fill extra APN information */ |
| get_apn_info_byMccMnc(APNS_EXTRA_FILENAME,mnc_data,1); |
| |
| |
| /*use default APN information in case there is no extra information*/ |
| attachDefaultParams(mnc_data); |
| return ret; |
| } |
| |
| |
| /** |
| * print APN information |
| * |
| * @param apn_ptr APN information struct to print |
| */ |
| void printApn(Apn_Info *apn_ptr) |
| { |
| UNUSEDPARAM(apn_ptr); |
| CM_Log(printApn, "carrier=%s\n",apn_ptr->carrier); |
| CM_Log(printApn1, "apn=%s\n",apn_ptr->apn); |
| CM_Log(printApn2, "type=%s\n",apn_ptr->type); |
| CM_Log(printApn3, "protocol=%s\n",apn_ptr->protocol); |
| CM_Log(printApn4, "authtype=%s\n",apn_ptr->authtype); |
| CM_Log(printApn5, "mmsc=%s\n",apn_ptr->mmsc); |
| CM_Log(printApn6, "mmsport=%s\n",apn_ptr->mmsport); |
| CM_Log(printApn7, "mmsproxy=%s\n",apn_ptr->mmsproxy); |
| CM_Log(printApn8, "port=%s\n",apn_ptr->port); |
| CM_Log(printApn9, "proxy=%s\n",apn_ptr->proxy); |
| CM_Log(printApn10, "server=%s\n",apn_ptr->server); |
| CM_Log(printApn11, "usrname=%s\n",apn_ptr->usrname); |
| CM_Log(printApn12, "password=%s\n",apn_ptr->paswd); |
| CM_Log(printApn13, "pco=%s\n",apn_ptr->pco); |
| CM_Log(printApn14, "vendorspecific=%s\n",apn_ptr->vendorSpecific); |
| CM_Log(printApn15, "roaming_protocol=%s\n",apn_ptr->roamingProtocol); |
| CM_Log(printApn16, "bearer=%s\n",apn_ptr->bearer); |
| CM_Log(printApn17, "Extra params:\n"); |
| CM_Log(printApn18, "always_on=%d\n",apn_ptr->Extra_params.always_on); |
| CM_Log(printApn19, "autoconnect=%d\n",apn_ptr->Extra_params.autoconnect); |
| CM_Log(printApn20, "config_only=%d\n",apn_ptr->Extra_params.config_only); |
| CM_Log(printApn21, "data_on_roaming=%d\n",apn_ptr->Extra_params.data_on_roaming); |
| CM_Log(printApn22, "mtu=%d\n",apn_ptr->Extra_params.mtu); |
| CM_Log(printApn23, "is_host=%d\n",apn_ptr->Extra_params.is_host); |
| CM_Log(printApn24, "lte_default=%d\n",apn_ptr->Extra_params.lte_default); |
| CM_Log(printApn25, "tetherable=%d\n",apn_ptr->Extra_params.tetherable); |
| } |
| |
| |
| /** |
| * print all APN's information according to mcc && mnc. |
| * |
| * @param mnc_data APN's struct to print,already containing mcc&mnc |
| */ |
| void printApnInfo (Mnc_Apn *mnc_data){ |
| int i; |
| Apn_Info* apn_ptr; |
| |
| //run over all the APN's for the given mcc,mnc |
| for (i=0;i<MAX_APN_NUM;i++) { |
| apn_ptr = &(mnc_data->apn_info_list[i]); |
| |
| if (!apn_ptr) |
| return; //we run over all the APN list |
| |
| /*check that APN params have been configured*/ |
| if (apn_ptr->basic_set == 0) |
| return; |
| CM_Log(printApnInfo, "APN %d:\n",i); |
| CM_Log(printApnInfo1, "=====\n"); |
| printApn(apn_ptr); //print APN params |
| } |
| return; |
| } |
| |
| #if CONFIG_LIBXML2 |
| /** |
| * asumming mcc,already received from imsi. |
| * get mnc length |
| * |
| * @param docname xml filename (database) |
| * @param mcc mcc value |
| * |
| * @return mnc length (2 or 3 digits) |
| */ |
| int get_mnc_length(char *docname,char *mcc) { |
| |
| xmlTextReaderPtr reader; |
| int ret,mnc_len = 2; |
| xmlChar *node_mcc; |
| xmlChar *node_mnc; |
| |
| reader = xmlNewTextReaderFilename(docname); |
| if (reader != NULL ) { |
| ret = xmlTextReaderRead(reader); |
| while (ret == 1) { |
| node_mcc = xmlTextReaderGetAttribute(reader,(const xmlChar *)"mcc"); |
| node_mnc = xmlTextReaderGetAttribute(reader,(const xmlChar *)"mnc"); |
| if (!xmlStrcmp(node_mcc, (const xmlChar *)mcc)) { |
| mnc_len=strlen((const char *)node_mnc); |
| xmlFree(node_mcc); |
| xmlFree(node_mnc); |
| break; |
| }else{ |
| xmlFree(node_mcc); |
| xmlFree(node_mnc); |
| } |
| ret = xmlTextReaderRead(reader); |
| } |
| xmlFreeTextReader(reader); |
| if (ret == -1) { |
| CM_Log(get_mnc_length, "%s : failed to parse\n", docname); |
| return 0; |
| } |
| } else { |
| CM_Log(get_mnc_length1, "Unable to open %s\n", docname); |
| return 0; |
| } |
| return mnc_len; |
| } |
| #endif |