背景:
项目开发用的是RK3399开发板,由于在测试网络中发现RK自身的有线网卡存在一些问题,所以需要使用USB转网卡过渡下。
【1】、查看当前设备中存在哪些网卡可用
可以看到目前有线网卡只有 eth0可用,我们需要切换成 eth1,并且使其能够配置ip。
进入 /sys/class/net/下查看当前有哪些网卡。
【2】早期初步尝试
通过命令设置eth1,并且给其写ip,使其可用。
启用USB网卡步骤:
插上USB网卡,连接网线,在adb shell下执行:
su //获取特权
ip -4 addr add 10.1.0.134/16 dev eth1 //给eth1设置ip地址
ifconfig eth1 up // 设置eth1可用
这样会存在两个问题:
1、ip地址配置不灵活,无法动态配置。2、重启设备之后,又不生效。**
【3】再次分析尝试
3.1、 再次分析,这个改动最好是从底层触发,因为这个是系统,偏底层行为,分析安卓以太网配置底层源码,看看能不能从底层找到突破口。
在源码 /frameworks/opt/net/ethernet/java/com/android/server/ethernet/EthernetServiceImpl.java
@Override
public void setConfiguration(IpConfiguration config) {
if (!mStarted.get()) {
Log.w(TAG, "System isn't ready enough to change ethernet configuration");
}
enforceConnectivityInternalPermission();
Log.d(TAG, "setConfiguration1: " + config.pppoeAccount + ", " + config.pppoePassword);
synchronized (mIpConfiguration) {
mEthernetConfigStore.writeIpAndProxyConfigurations(config);
// TODO: this does not check proxy settings, gateways, etc.
// Fix this by making IpConfiguration a complete representation of static configuration.
if (true) {
mIpConfiguration = new IpConfiguration(config);
if (false) { // old android original method
mTracker.stop();
mTracker.start(mContext, mHandler);
} else { // new method
mEthface="eth0";
}
}
mTracker.reconnect(mEthface);
}
}
}
系统指定了 “eth0”,作为默认的有线网卡,这个也就解释了为什么我们用命令设置完,重启设备后就不生效的原因了。^_^
那找到了,就好改了,将“eth0”改为“eth1”.
mTracker.reconnect(mEthface) 这个类负责去连接,我们进一步跟踪。
2、mTracker 对应的是 /frameworks/opt/net/ethernet/java/com/android/server/ethernet/EthernetNetworkFactory.java
// first disconnect, then connect
public void reconnect(String iface) {
Log.d(TAG, "reconnect:");
mReconnecting = true;
if (iface == null)
iface = mIface;
Log.d(TAG, "first disconnect");
updateInterfaceState(iface, false);
try {
Thread.sleep(1000);
} catch (InterruptedException ignore) {
}
Log.d(TAG, "then connect");
updateInterfaceState(iface, true);
mReconnecting = false;
}
可以看到该方法主要是更新以太网卡,如果上面只改了eth1,并不能使其生效,对照设置eth1的命令,我们并没有up起eth1,在该类中找到 setInterfaceUp(String iface)方法,该方法是在系统启动以太网服务时候调用,进一步看什么方法调用了setInterfaceUp。
private boolean maybeTrackInterface(String iface) {
// If we don't already have an interface, and if this interface matches
// our regex, start tracking it.
if (!iface.matches(mIfaceMatch) || isTrackingInterface())
return false;
Log.d(TAG, "Started tracking interface " + iface);
if(!TextUtils.isEmpty(mEthface)) {
iface = mEthface;
}
setInterfaceUp(iface);
return true;
}
该方法其实也没有做什么事情,就是判断iface的格式,然后设置其可用,所以我们在这个方法里面也使其指定 eth1,这样就大功告成了。
综上:1、在 EthernetNetworkFactory 中指定 eth1,这里的作用是系统启动以太网服务时候就指定好,并且使该网卡可 用。
2、在EthernetServiceImpl.java中,也指定eth1,使其动态配置时候,就直接给其分配地址。