Android U 匹配不到APN,无法发起数据建立的问题分析

2023-11-22 19:04

本文主要是介绍Android U 匹配不到APN,无法发起数据建立的问题分析,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

问题

打开数据开关后,没有data PDN请求发起,因此无法上网。

根据日志确定是没有找到合适的data profile,原因一般有:

1、APN 没有配置

2、APN 类型/网络能力不满足——APN type或bearer

3、APN 配置了但被disable了——APN proofile的carrierEnable值

日志分析

fail log:

APN 被disable了,所以无法匹配。

//preferred=true说明当前选中的是此条APN

11-20 15:01:51.409140  2316  3480 D DPM-0   : getApnSettingForNetworkRequest: networkType=13 isMtkImsDataSupport=true hasEimsCapability=false mPreferredDataProfile=[DataProfile=[ApnSetting]....] dataProfilesCount=0 dataProfiles=[] mAllDataProfiles=[[DataProfile=[ApnSetting] INTERNET, 3080, xxxxxx, internet, , null, , null, null, 0, supl | hipri | default, IPV4V6, IP, false, 0, true, 0, 0, 0, 0, 0, gid, xxxxx000000000000, false, UNKNOWN, UNKNOWN, 0, -1, -1, false, 961, TrafficDescriptor={mDnn=internet, null}, preferred=true]...]
11-20 15:01:51.410224  2316  3480 D DPM-0   : Can't find any data profile that can satisfy [NetworkRequest [ NONE id=0, [ Capabilities: DUN&TRUSTED&NOT_VPN&NOT_VCN_MANAGED Uid: 1001 UnderlyingNetworks: Null] ], mPriority=30, state=UNSATISFIED, mAttachedDataNetwork=null, isMetered=true, created time=15:01:51.407, evaluation result=null]
11-20 15:01:51.411224  1366  1366 D ImsManager: [1] Registration callback removed.
11-20 15:01:51.413463  2316  3480 D DPM-0   : Unable to find a data profile for [NetworkRequest [ NONE id=0, [ Capabilities: DUN&TRUSTED&NOT_VPN&NOT_VCN_MANAGED Uid: 1001 UnderlyingNetworks: Null] ], mPriority=30, state=UNSATISFIED, mAttachedDataNetwork=null, isMetered=true, created time=15:01:51.408, evaluation result=null]

正常日志:

dataProfilesCount 指明网络能力匹配的APN数

11-20 15:19:20.723854  2316  2316 D DPM-0   : getApnSettingForNetworkRequest: networkType=13 isMtkImsDataSupport=true hasEimsCapability=false mPreferredDataProfile=[DataProfile=[ApnSetting] ....] dataProfilesCount=1 dataProfiles=[[DataProfile=[ApnSetting] 

11-20 15:19:20.725075  2316  2316 V DPM-0   : Satisfied profile: [DataProfile=[ApnSetting]

11-20 15:19:20.725871  2316  2316 D DPM-0   : The final available profile: [DataProfile=[ApnSetting] 

11-20 15:19:20.729504  2316  2316 D DNC-0   : Data evaluation: evaluation reason:NEW_REQUEST, Data allowed reason: NORMAL, candidate profile=[DataProfile=[ApnSetting] 

11-20 15:19:20.730116  2316  2316 D DNC-0   : onSetupDataNetwork: dataProfile=[DataProfile=[ApnSetting] 

11-20 15:19:20.731688  2316  2316 D DNC-0   : Creating data network on WWAN with [DataProfile=[ApnSetting] 

11-20 15:19:20.768286  2316  2316 D DSM-C-0 : setupDataCall

11-20 15:19:20.769505  2316  2316 D DN-114-C: ConnectingState: setupData: accessNetwork=EUTRAN, [DataProfile=[ApnSetting] ...], isModemRoaming=false, allowRoaming=true, PDU session id=0, matchAllRuleAllowed=true
11-20 15:19:20.776007  2316  2682 D RILJ    :

 [0868]> SETUP_DATA_CALL,reason=NORMAL,accessNetworkType=EUTRAN,dataProfile=[DataProfile=[ApnSetting] ..],isRoaming=false,allowRoaming=true,linkProperties=null,pduSessionId=0,sliceInfo=null,trafficDescriptor=TrafficDescriptor={mDnn=VZWADMIN, null},matchAllRuleAllowed=true [PHONE0]

11-20 15:19:21.063568  2316  2674 D RILJ    : [0868]< SETUP_DATA_CALL DataCallResponse: { cause=NONE(0x0) retry=-1 cid=1803 linkStatus=2 protocolType=2 ifname=ccmni3 addresses=[10.128.159.113/32, 2600:100f:f00c:330f:0:56:6fe2:e801/64] dnses=[/2001:4888:53:ff00:524:d::, /2001:4888:52:ff00:528:d::, /198.224.166.135, /198.224.167.135] gateways=[/10.128.159.113, /::] pcscf=[] mtu=1428 mtuV4=1428 mtuV6=1428 handoverFailureMode=unknown pduSessionId=0 defaultQos=EpsQos { qosClassId=8 downlink=Bandwidth { maxBitrateKbps=0 guaranteedBitrateKbps=0} uplink=Bandwidth { maxBitrateKbps=0 guaranteedBitrateKbps=0}} qosBearerSessions=[] sliceInfo=null trafficDescriptors=[]} [PHONE0]

 代码分析

DataProfileManager.java - 【frameworks/opt/telephony】

/*** Get the APN setting for the network request.** @param networkRequest The network request.* @param networkType The current data network type.* @param ignorePermanentFailure {@code true} to ignore {@link ApnSetting#getPermanentFailed()}.* This should be set to true for condition-based retry/setup.* @return The APN setting. {@code null} if can't find any satisfiable data profile.*/
private @Nullable ApnSetting getApnSettingForNetworkRequest(@NonNull TelephonyNetworkRequest networkRequest, @NetworkType int networkType,boolean ignorePermanentFailure) {if (!networkRequest.hasAttribute(TelephonyNetworkRequest.CAPABILITY_ATTRIBUTE_APN_SETTING)) {loge("Network request does not have APN setting attribute.");return null;}//1、优先选择preferred APN,如果满足并且不处于PermanentFailure状态则直接请求// If the preferred data profile can be used, always use it if it can satisfy the network// request with current network type (even though it's been marked as permanent failed.)if (mPreferredDataProfile != null&& networkRequest.canBeSatisfiedBy(mPreferredDataProfile)&& mPreferredDataProfile.getApnSetting() != null&& mPreferredDataProfile.getApnSetting().canSupportNetworkType(networkType)) {if (ignorePermanentFailure || !mPreferredDataProfile.getApnSetting().getPermanentFailed()) {return mPreferredDataProfile.getApnSetting();}log("The preferred data profile is permanently failed. Only condition based retry "+ "can happen.");return null;}//2、如果没有首选数据配置文件,则过滤掉不能满足网络请求的数据配置文件//Note:找不到profile 一般就是这里匹配不到了// Filter out the data profile that can't satisfy the request.// Preferred data profile should be returned in the top of the list.List<DataProfile> dataProfiles = mAllDataProfiles.stream().filter(networkRequest::canBeSatisfiedBy)// The longest time hasn't used data profile will be in the front so all the data// profiles can be tried..sorted(Comparator.comparing(DataProfile::getLastSetupTimestamp))    //并按照它们的最后设置时间进行排序,将最长时间未使用的数据配置文件放在列表的前面.collect(Collectors.toList());for (DataProfile dataProfile : dataProfiles) {    //然后尝试筛选并使用它们来满足网络请求。logv("Satisfied profile: " + dataProfile + ", last setup="+ DataUtils.elapsedTimeToString(dataProfile.getLastSetupTimestamp()));}if (dataProfiles.size() == 0) {log("Can't find any data profile that can satisfy " + networkRequest);return null;}// Check if the remaining data profiles can used in current data network type.dataProfiles = dataProfiles.stream().filter(dp -> dp.getApnSetting() != null&& dp.getApnSetting().canSupportNetworkType(networkType)).collect(Collectors.toList());if (dataProfiles.size() == 0) {log("Can't find any data profile for network type "+ TelephonyManager.getNetworkTypeName(networkType));return null;}// Check if preferred data profile set id matches.dataProfiles = dataProfiles.stream().filter(dp -> dp.getApnSetting() != null&& (dp.getApnSetting().getApnSetId()== Telephony.Carriers.MATCH_ALL_APN_SET_ID|| dp.getApnSetting().getApnSetId() == mPreferredDataProfileSetId)).collect(Collectors.toList());if (dataProfiles.size() == 0) {log("Can't find any data profile has APN set id matched. mPreferredDataProfileSetId="+ mPreferredDataProfileSetId);return null;}// Check if data profiles are permanently failed.dataProfiles = dataProfiles.stream().filter(dp -> ignorePermanentFailure || !dp.getApnSetting().getPermanentFailed()).collect(Collectors.toList());if (dataProfiles.size() == 0) {log("The suitable data profiles are all in permanent failed state.");return null;}return dataProfiles.get(0).getApnSetting();
}
排查接口

canBeSatisfiedBy in TelephonyNetworkRequest.java -【frameworks/opt/telephony】

canHandleType in ApnSetting.java【frameworks/base/telephony】


匹配不到关键就是在网络能力评估的过程,canBeSatisfiedBy会根据APN类型筛选能力匹配的项,在canHandleType检查完APN可用性之后,返回enable且符合网络的APN。

/**
* Check if this network request can be satisfied by a data profile.
*
* @param dataProfile The data profile to check.
* @return {@code true} if this network request can be satisfied by the data profile.
*/
public boolean canBeSatisfiedBy(@NonNull DataProfile dataProfile) {// If the network request can be translated to OS/App id, then check if the data profile's// OS/App id can satisfy it.if (hasAttribute(CAPABILITY_ATTRIBUTE_TRAFFIC_DESCRIPTOR_OS_APP_ID)&& getOsAppId() != null) {// The network request has traffic descriptor type capabilities. Match the traffic// descriptor.if (dataProfile.getTrafficDescriptor() != null && Arrays.equals(getOsAppId().getBytes(),dataProfile.getTrafficDescriptor().getOsAppId())) {return true;}}// If the network request can be translated to APN setting or DNN in traffic descriptor,// then check if the data profile's APN setting can satisfy it.if ((hasAttribute(CAPABILITY_ATTRIBUTE_APN_SETTING)|| hasAttribute(CAPABILITY_ATTRIBUTE_TRAFFIC_DESCRIPTOR_DNN))&& dataProfile.getApnSetting() != null) {// Fallback to the legacy APN type matching.List<Integer> apnTypes = Arrays.stream(getCapabilities()).boxed().map(DataUtils::networkCapabilityToApnType).filter(apnType -> apnType != ApnSetting.TYPE_NONE).collect(Collectors.toList());// In case of enterprise network request, the network request will have internet,// but APN type will not have default type as the enterprise apn should not be used// as default network. Ignore default type of the network request if it// has enterprise type as well. This will make sure the network request with// internet and enterprise will be satisfied with data profile with enterprise at the// same time default network request will not get satisfied with enterprise data// profile.// TODO b/232264746if (apnTypes.contains(ApnSetting.TYPE_ENTERPRISE)) {apnTypes.remove((Integer) ApnSetting.TYPE_DEFAULT);}return apnTypes.stream().allMatch(dataProfile.getApnSetting()::canHandleType);}return false;
}/** @hide */
public boolean canHandleType(@ApnType int type) {if (!mCarrierEnabled) {return false;}// DEFAULT can handle HIPRI.return hasApnType(type);
}

定位原因的方法

查看APNSettings配置是否正确,以上问题就是APN配置了但被disable了。

[DataProfile=[ApnSetting] INTERNET, 3080, xxxxxx, internet, , null, , null, null, 0, supl | hipri | default, IPV4V6, IP, false, 0, true, 0, 0, 0, 0, 0, gid, xxxxx000000000000, false, UNKNOWN, UNKNOWN, 0, -1, -1, false, 961, TrafficDescriptor={mDnn=internet, null}, preferred=true]

根据ApnSettings实体节后打印信息,mCarrierEnabled就是上述日志false的位置。

/*** Returns the string representation of ApnSetting.** This method prints null for unset elements. The output doesn't contain password or user.* @hide*/
public String toString() {StringBuilder sb = new StringBuilder();sb.append("[ApnSetting] ").append(mEntryName).append(", ").append(mId).append(", ").append(mOperatorNumeric).append(", ").append(mApnName).append(", ").append(mProxyAddress).append(", ").append(UriToString(mMmsc)).append(", ").append(mMmsProxyAddress).append(", ").append(portToString(mMmsProxyPort)).append(", ").append(portToString(mProxyPort)).append(", ").append(mAuthType).append(", ");final String[] types = getApnTypesStringFromBitmask(mApnTypeBitmask).split(",");sb.append(TextUtils.join(" | ", types));sb.append(", ").append(PROTOCOL_INT_MAP.get(mProtocol));sb.append(", ").append(PROTOCOL_INT_MAP.get(mRoamingProtocol));sb.append(", ").append(mCarrierEnabled);    //APN启用情况sb.append(", ").append(mProfileId);sb.append(", ").append(mPersistent);sb.append(", ").append(mMaxConns);sb.append(", ").append(mWaitTime);sb.append(", ").append(mMaxConnsTime);sb.append(", ").append(mMtuV4);sb.append(", ").append(mMtuV6);sb.append(", ").append(MVNO_TYPE_INT_MAP.get(mMvnoType));sb.append(", ").append(mMvnoMatchData);sb.append(", ").append(mPermanentFailed);sb.append(", ").append(TelephonyManager.convertNetworkTypeBitmaskToString(mNetworkTypeBitmask));sb.append(", ").append(TelephonyManager.convertNetworkTypeBitmaskToString(mLingeringNetworkTypeBitmask));sb.append(", ").append(mApnSetId);sb.append(", ").append(mCarrierId);sb.append(", ").append(mSkip464Xlat);sb.append(", ").append(mAlwaysOn);sb.append(", ").append(Objects.hash(mUser, mPassword));return sb.toString();
}

这篇关于Android U 匹配不到APN,无法发起数据建立的问题分析的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/412266

相关文章

大模型研发全揭秘:客服工单数据标注的完整攻略

在人工智能(AI)领域,数据标注是模型训练过程中至关重要的一步。无论你是新手还是有经验的从业者,掌握数据标注的技术细节和常见问题的解决方案都能为你的AI项目增添不少价值。在电信运营商的客服系统中,工单数据是客户问题和解决方案的重要记录。通过对这些工单数据进行有效标注,不仅能够帮助提升客服自动化系统的智能化水平,还能优化客户服务流程,提高客户满意度。本文将详细介绍如何在电信运营商客服工单的背景下进行

基于MySQL Binlog的Elasticsearch数据同步实践

一、为什么要做 随着马蜂窝的逐渐发展,我们的业务数据越来越多,单纯使用 MySQL 已经不能满足我们的数据查询需求,例如对于商品、订单等数据的多维度检索。 使用 Elasticsearch 存储业务数据可以很好的解决我们业务中的搜索需求。而数据进行异构存储后,随之而来的就是数据同步的问题。 二、现有方法及问题 对于数据同步,我们目前的解决方案是建立数据中间表。把需要检索的业务数据,统一放到一张M

关于数据埋点,你需要了解这些基本知识

产品汪每天都在和数据打交道,你知道数据来自哪里吗? 移动app端内的用户行为数据大多来自埋点,了解一些埋点知识,能和数据分析师、技术侃大山,参与到前期的数据采集,更重要是让最终的埋点数据能为我所用,否则可怜巴巴等上几个月是常有的事。   埋点类型 根据埋点方式,可以区分为: 手动埋点半自动埋点全自动埋点 秉承“任何事物都有两面性”的道理:自动程度高的,能解决通用统计,便于统一化管理,但个性化定

使用SecondaryNameNode恢复NameNode的数据

1)需求: NameNode进程挂了并且存储的数据也丢失了,如何恢复NameNode 此种方式恢复的数据可能存在小部分数据的丢失。 2)故障模拟 (1)kill -9 NameNode进程 [lytfly@hadoop102 current]$ kill -9 19886 (2)删除NameNode存储的数据(/opt/module/hadoop-3.1.4/data/tmp/dfs/na

异构存储(冷热数据分离)

异构存储主要解决不同的数据,存储在不同类型的硬盘中,达到最佳性能的问题。 异构存储Shell操作 (1)查看当前有哪些存储策略可以用 [lytfly@hadoop102 hadoop-3.1.4]$ hdfs storagepolicies -listPolicies (2)为指定路径(数据存储目录)设置指定的存储策略 hdfs storagepolicies -setStoragePo

Hadoop集群数据均衡之磁盘间数据均衡

生产环境,由于硬盘空间不足,往往需要增加一块硬盘。刚加载的硬盘没有数据时,可以执行磁盘数据均衡命令。(Hadoop3.x新特性) plan后面带的节点的名字必须是已经存在的,并且是需要均衡的节点。 如果节点不存在,会报如下错误: 如果节点只有一个硬盘的话,不会创建均衡计划: (1)生成均衡计划 hdfs diskbalancer -plan hadoop102 (2)执行均衡计划 hd

好题——hdu2522(小数问题:求1/n的第一个循环节)

好喜欢这题,第一次做小数问题,一开始真心没思路,然后参考了网上的一些资料。 知识点***********************************无限不循环小数即无理数,不能写作两整数之比*****************************(一开始没想到,小学没学好) 此题1/n肯定是一个有限循环小数,了解这些后就能做此题了。 按照除法的机制,用一个函数表示出来就可以了,代码如下

hdu1043(八数码问题,广搜 + hash(实现状态压缩) )

利用康拓展开将一个排列映射成一个自然数,然后就变成了普通的广搜题。 #include<iostream>#include<algorithm>#include<string>#include<stack>#include<queue>#include<map>#include<stdio.h>#include<stdlib.h>#include<ctype.h>#inclu

性能分析之MySQL索引实战案例

文章目录 一、前言二、准备三、MySQL索引优化四、MySQL 索引知识回顾五、总结 一、前言 在上一讲性能工具之 JProfiler 简单登录案例分析实战中已经发现SQL没有建立索引问题,本文将一起从代码层去分析为什么没有建立索引? 开源ERP项目地址:https://gitee.com/jishenghua/JSH_ERP 二、准备 打开IDEA找到登录请求资源路径位置

三国地理揭秘:为何北伐之路如此艰难,为何诸葛亮无法攻克陇右小城?

俗话说:天时不如地利,不是随便说说,诸葛亮六出祁山,连关中陇右的几座小城都攻不下来,行军山高路险,无法携带和建造攻城器械,是最难的,所以在汉中,无论从哪一方进攻,防守方都是一夫当关,万夫莫开;再加上千里运粮,根本不需要打,司马懿只需要坚守城池拼消耗就能不战而屈人之兵。 另一边,洛阳的虎牢关,一旦突破,洛阳就无险可守,这样的进军路线,才是顺势而为的用兵之道。 读历史的时候我们常常看到某一方势