系列目录 :第一篇:全景图与调用链路概览 | 第二篇:内核层---netfilter/iptables与路由策略 | 第三篇:Native层(上)---netd守护进程与CommandListener | 第四篇:Native层(下)---netd Controller详解 | 第五篇:Framework层(上)---ConnectivityService核心机制 | 第六篇:Framework层(下)---NMS/NPMS/NSS三大服务 | 第七篇:连接建立---WiFi/移动数据/以太网完整流程 | 第八篇:应用API层---ConnectivityManager使用与实战调试
一、为什么要系统学习 Android 网络模块
每个 Android 开发者都写过 HttpURLConnection.connect(),当这个调用没有按预期返回数据时,问题可能出在哪一层?是 DNS 解析被 netd 代理拦截了?是 netfilter 防火墙规则丢弃了包?还是 ConnectivityService 错误地切换了默认网络?
网络是 Android 设备最核心的能力之一。从应用发起一个 HTTP 请求,到数据包从 WiFi 或 4G 接口发出,中间经过了 Linux 内核协议栈、netd 守护进程、Framework 层的多个服务、以及各类网络代理------每一步都可能成为问题排查的关键环节。
当遇到以下问题时,仅凭 Google 搜索是远远不够的:
- "WiFi 已连接但无法上网":是 DNS 解析失败?是路由表配置错误?还是 netfilter 防火墙规则阻止了流量?
- "WiFi 切换到移动数据太慢":ConnectivityService 的评分机制是怎么判断的?NetworkAgent 的注册和注销流程是什么?
- "VPN 连上后网络断了":netd 的 RouteController 如何管理 fwmark?多网络并存时路由策略如何协调?
- "热点共享失败":TetherController 的 NAT 转发规则是怎么生成的?接口桥接和 DHCP 配置在哪个环节?
本系列以 AOSP 7(android-7.1.2_r36) 为基准,带你从 Linux 内核一路走到 Android 应用 API,逐层拆解 Android 网络子系统。
二、宏观架构:五层模型
Android 网络系统可以用一个清晰的五层模型来描述:
┌─────────────────────────────────────────────────────────────┐
│ 应用 API 层 │
│ ConnectivityManager / WifiManager / NetworkRequest │
│ NetworkCallback / bindProcessToNetwork() │
├─────────────────────────────────────────────────────────────┤
│ 网络代理层 (NetworkAgent) │
│ WifiStateMachine → WiFi 连接的代理 │
│ DataConnection → 移动数据的代理 │
│ EthernetNetworkFactory → 以太网的代理 │
├─────────────────────────────────────────────────────────────┤
│ Framework 服务层 │
│ ConnectivityService → 网络连接状态机、评分与切换 │
│ NetworkManagementService → 与 netd 通信、接口管理 │
│ NetworkPolicyManagerService → 网络策略(省电/流量限制) │
│ NetworkStatsService → 按 UID/接口 统计流量 │
├─────────────────────────────────────────────────────────────┤
│ Native 守护进程层 │
│ netd (Network Daemon) │
│ ├── CommandListener → 接收并分发 Framework 层命令 │
│ ├── NetlinkManager → 监听内核 netlink 事件 │
│ ├── DnsProxyListener → DNS 代理(拦截所有 DNS 请求) │
│ ├── NetworkController → 接口管理 │
│ ├── RouteController → 路由表与 fwmark 策略 │
│ ├── FirewallController → 基于 UID 的 iptables 防火墙 │
│ ├── BandwidthController → 带宽控制 │
│ ├── TetherController → USB/WiFi 网络共享 │
│ ├── IdletimerController → 接口空闲检测 │
│ └── SoftapController → WiFi 热点管理 │
├─────────────────────────────────────────────────────────────┤
│ 内核层 │
│ Linux netfilter/iptables / 路由表 / fwmark │
│ 网络设备驱动 (wlan0 / rmnet0 / eth0 / tun0) │
└─────────────────────────────────────────────────────────────┘
三、核心组件速览
3.1 netd --- 网络管理守护进程
netd 是 Android 网络管理的枢纽,位于 Framework 和内核之间:
- 向下通过 NetlinkManager 监听内核 UEvent 事件(接口插拔、链路状态等)
- 向上通过 CommandListener 接收来自 NetworkManagementService 的命令
- 内部通过各类 Controller 操作 iptables、路由表、DNS 配置等
- 为应用提供 DNS 代理服务(DnsProxyListener)
源码路径 :system/core/rootdir/init.rc
bash
service netd /system/bin/netd
class main
socket netd stream 0660 root system
socket dnsproxyd stream 0660 root inet
socket mdns stream 0660 root system
socket fwmarkd stream 0660 root inet
关键设计 :netd 通过四个独立的 Socket 实现职责分离------控制命令、DNS 代理、服务发现、fwmark 各走各的通道,互不干扰。Framework 层通过
netdsocket 下发命令,所有应用的 DNS 查询则统一走dnsproxydsocket。
四个 Socket 各司其职:
| Socket | 类型 | 权限 | 用途 |
|---|---|---|---|
| netd | stream | 0660 root system | Framework 层控制命令通道 |
| dnsproxyd | stream | 0660 root inet | DNS 代理,所有进程的 DNS 查询都走这里 |
| mdns | stream | 0660 root system | 多播 DNS 服务发现 |
| fwmarkd | stream | 0660 root inet | fwmark 命令通道 |
3.2 ConnectivityService --- 网络总调度
ConnectivityService 是 Framework 层的网络状态机,负责:
- 管理所有 NetworkAgent(WiFi、移动数据、以太网等)
- 根据 NetworkFactory 的评分决定使用哪个网络
- 处理 NetworkRequest(应用请求网络)
- 协调多网络并存时的路由策略
- 发送 CONNECTIVITY_ACTION 广播通知应用
源码路径 :frameworks/base/services/core/java/com/android/server/ConnectivityService.java
3.3 NetworkManagementService --- netd 通信桥梁
NetworkManagementService 通过 NativeDaemonConnector 与 netd 的 CommandListener 通信,封装了所有 netd 命令的发送和响应解析。
源码路径 :frameworks/base/services/core/java/com/android/server/NetworkManagementService.java
3.4 NetworkAgent / NetworkFactory --- 网络代理模式
每种网络类型都有自己的 NetworkFactory(工厂)和 NetworkAgent(代理):
WifiStateMachine:既是 WiFi 的状态机,也是一个 NetworkAgentDataConnection(telephony):移动数据的连接,注册为 NetworkAgentEthernetNetworkFactory:以太网的工厂 + 代理
源码路径:
frameworks/base/core/java/android/net/NetworkAgent.javaframeworks/base/core/java/android/net/NetworkFactory.java
四、一条 HTTP 请求的完整旅程
以应用发起 HttpURLConnection.connect() 为例,跟踪数据包的完整路径:
T0: APP 调用 URL.openConnection()
→ HttpURLConnection.connect()
→ 创建 Socket
T1: Socket 连接
→ 查询 DNS:getaddrinfo()
→ 通过 /dev/socket/dnsproxyd 转发到 netd 的 DnsProxyListener
→ netd 查询上游 DNS 服务器
T2: TCP 三次握手
→ Socket.connect()
→ 内核 TCP 协议栈
→ netfilter OUTPUT 链(防火墙检查)
→ netfilter POSTROUTING 链(NAT 转换)
→ 路由表查询(fwmark 选择正确的路由表)
→ 网卡驱动发送 (wlan0 / rmnet_data0)
T3: HTTP 请求发送
→ write(request)
→ 同上路径
T4: HTTP 响应接收
→ 网卡驱动接收
→ netfilter PREROUTING 链
→ TCP 协议栈 → Socket → APP
T5: 连接关闭
→ Socket.close()
关键路径:注意 DNS 查询(T1)和路由选择(T2)是两个最关键的决策点------DNS 决定"往哪去",路由表决定"从哪走",两者共同决定了数据包的最终出口。
五、多网络并存的挑战
Android 的一大特色是多网络并存:WiFi 连着、移动数据也连着、VPN 也连着,它们如何协调?
关键在于 netId + fwmark + 策略路由 的组合(以下为概念示意,具体实现见第四篇 RouteController 详解):
netId=100 (WiFi) → 路由表 100 → 默认走 wlan0
netId=101 (移动数据) → 路由表 101 → 默认走 rmnet_data0
netId=102 (VPN) → 路由表 102 → 默认走 tun0
每个 Socket 创建时会根据绑定规则获得一个 fwmark,内核根据 fwmark 查找对应的策略路由表:
Socket → fwmark=0x00030064 (netId=100)
→ 策略路由规则 → 查找路由表 100
→ 默认路由指向 wlan0
关键设计:fwmark 是 Socket 的"网络身份证"------内核根据它决定查询哪张路由表,从而实现多网络并存时的流量隔离,避免 WiFi 和移动数据的路由互相干扰。
ConnectivityService 在切换默认网络时,会更新全局 fwmark 和路由,确保未绑定到特定网络的应用走正确的出口。
六、关键源码文件索引
以下表格按模块汇总了本系列涉及的核心源码文件,方便读者在阅读后续各篇时快速定位:
netd 守护进程
| 文件 | 说明 |
|---|---|
system/netd/server/main.cpp |
netd 入口 |
system/netd/server/CommandListener.cpp |
命令监听与分发 |
system/netd/server/NetlinkManager.cpp |
内核事件监听 |
system/netd/server/NetworkController.cpp |
接口管理 |
system/netd/server/RouteController.cpp |
路由策略 |
system/netd/server/DnsProxyListener.cpp |
DNS 代理 |
system/netd/server/ResolverController.cpp |
DNS 解析器 |
system/netd/server/FirewallController.cpp |
防火墙 |
system/netd/server/BandwidthController.cpp |
带宽控制 |
system/netd/server/TetherController.cpp |
网络共享 |
system/netd/server/SoftapController.cpp |
WiFi 热点 |
system/netd/server/IdletimerController.cpp |
空闲检测 |
Framework 层
| 文件 | 说明 |
|---|---|
frameworks/base/services/core/java/com/android/server/ConnectivityService.java |
网络总调度 |
frameworks/base/services/core/java/com/android/server/NetworkManagementService.java |
netd 通信桥梁 |
frameworks/base/services/core/java/com/android/server/net/NetworkPolicyManagerService.java |
网络策略 |
frameworks/base/services/core/java/com/android/server/net/NetworkStatsService.java |
流量统计 |
frameworks/base/services/core/java/com/android/server/NativeDaemonConnector.java |
与 netd 的命令通信协议 |
NetworkAgent / 网络类型
| 文件 | 说明 |
|---|---|
frameworks/base/core/java/android/net/NetworkAgent.java |
网络代理基类 |
frameworks/base/core/java/android/net/NetworkFactory.java |
网络工厂基类 |
frameworks/opt/net/wifi/service/java/com/android/server/wifi/WifiStateMachine.java |
WiFi 状态机 |
应用 API
| 文件 | 说明 |
|---|---|
frameworks/base/core/java/android/net/ConnectivityManager.java |
应用网络 API |
frameworks/base/core/java/android/net/NetworkRequest.java |
网络请求构建 |
frameworks/base/core/java/android/net/Network.java |
网络连接句柄 |
七、本篇总结
本篇建立了 Android 7 网络子系统的五层全景图(内核 → netd → Framework → NetworkAgent → 应用 API),并跟踪了一条 HTTP 请求在各层之间穿行的完整路径。核心结论:
关键理解:netd 是网络控制的中枢------Framework 层的所有网络策略(防火墙、带宽、路由、DNS)最终都通过 netd 的 Controller 落地为 iptables 规则和路由表条目。理解 netd,就理解了 Android 网络的"操作系统"。
从下一篇开始,我们将从内核层逐层向上拆解,首先深入 netfilter/iptables 和 fwmark 策略路由机制。
八、各篇预告
| 篇目 | 聚焦 |
|---|---|
| 第二篇 | 内核层:netfilter/iptables、fwmark、路由策略 |
| 第三篇 | netd 启动、四个 Socket、CommandListener、NetlinkManager |
| 第四篇 | 八个 Controller 逐一详解 |
| 第五篇 | ConnectivityService 评分机制、网络切换 |
| 第六篇 | NMS/NPMS/NSS 三大服务:防火墙、策略、统计 |
| 第七篇 | WiFi/移动数据/以太网三种网络建立的完整源码流程 |
| 第八篇 | 实战调试:dumpsys/ndc/tcpdump + 6 个典型问题分析 |