/*
* Copyright (C) 2014 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.
*/
package com.android.server.ethernet;
import android.content.Context;
import android.net.ConnectivityManager;
import android.net.DhcpResults;
import android.net.EthernetManager;
import android.net.IEthernetServiceListener;
import android.net.InterfaceConfiguration;
import android.net.IpConfiguration;
import android.net.IpConfiguration.IpAssignment;
import android.net.IpConfiguration.ProxySettings;
import android.net.LinkProperties;
import android.net.LinkAddress;
import android.net.NetworkAgent;
import android.net.NetworkAgentConfig;
import android.net.NetworkCapabilities;
import android.net.NetworkFactory;
import android.net.NetworkInfo;
import android.net.NetworkCapabilities;
import android.net.NetworkInfo.DetailedState;
import android.net.StaticIpConfiguration;
import android.net.RouteInfo;
import android.os.Handler;
import android.os.IBinder;
import android.os.INetworkManagementService;
import android.os.Looper;
import android.os.RemoteCallbackList;
import android.os.RemoteException;
import android.os.ServiceManager;
import android.text.TextUtils;
import android.util.Log;
import android.content.Intent;
import android.os.UserHandle;
import android.provider.Settings;
import android.os.Message;
import android.os.HandlerThread;
import android.os.SystemProperties;
import android.net.ip.IIpClient;
import android.net.shared.ProvisioningConfiguration;
import android.net.ip.IpClientCallbacks;
import android.net.ip.IpClientUtil;
import android.os.ConditionVariable;
import com.android.internal.util.IndentingPrintWriter;
import com.android.server.net.BaseNetworkObserver;
import java.io.FileDescriptor;
import java.io.PrintWriter;
import java.io.File;
import java.io.BufferedReader;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStreamReader;
import java.lang.Exception;
import java.util.List;
import java.net.Inet4Address;
import android.net.INetd;
import java.net.InetAddress;
import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;
import android.net.InetAddresses;
class EthernetNetworkFactoryExt {
private static final String TAG = "EthernetNetworkFactoryExt";
private static String internalInterface = "eth1"; //lan
private static String externalInterface = "eth0"; //wan
private static boolean mLinkUp = false;
private static String mMode = "1"; // 0: DHCP; 1: Static
private static final int EVENT_INTERFACE_LINK_STATE_CHANGED = 0;
private static final int EVENT_INTERFACE_LINK_STATE_CHANGED_DELAY_MS = 1000;
private static final boolean DBG = true;
private static String mIface = "eth1";
private static String NETWORK_TYPE = "Ethernet1";
private final int mLegacyType = ConnectivityManager.TYPE_ETHERNET;
private final int NETWORK_SCORE = 100;
private INetworkManagementService mNMService;
private Context mContext;
private Handler mHandler;
private int mConnectState; //0: disconnect ; 1: connect; 2: connecting
private LinkProperties mLinkProperties;
private IIpClient mIpClient;
private StaticIpConfiguration.Builder mStaticIpConfiguration;
private IpConfiguration mIpConfiguration;
private IpClientCallbacksImpl mIpClientCallback;
private NetworkAgent mNetworkAgent;
private NetworkCapabilities mCapabilities;
final List<InetAddress> dnsServers = new ArrayList<>();
public EthernetNetworkFactoryExt() {
HandlerThread handlerThread = new HandlerThread("EthernetNetworkFactoryExtThread");
handlerThread.start();
mHandler = new EthernetNetworkFactoryExtHandler(handlerThread.getLooper(), this);
mConnectState = 0;
mIpClient = null;
mCapabilities = createDefaultNetworkCapabilities();
}
private class EthernetNetworkFactoryExtHandler extends Handler {
private EthernetNetworkFactoryExt mEthernetNetworkFactoryExt;
public EthernetNetworkFactoryExtHandler(Looper looper, EthernetNetworkFactoryExt factory) {
super(looper);
mEthernetNetworkFactoryExt = factory;
}
@Override
public void handleMessage(Message msg) {
switch (msg.what) {
case EVENT_INTERFACE_LINK_STATE_CHANGED:
if(msg.arg1 == 1) {
mEthernetNetworkFactoryExt.connect();
} else {
mEthernetNetworkFactoryExt.disconnect();
}
break;
}
}
}
private void setInterfaceUp(String iface) {
try {
mNMService.setInterfaceUp(iface);
} catch (Exception e) {
Log.e(TAG, "Error upping interface " + iface + ": " + e);
}
}
public void start(Context context, INetworkManagementService s) {
mContext = context;
mNMService = s;
mIpConfiguration = new IpConfiguration();
try {
final String[] ifaces = mNMService.listInterfaces();
Log.e(TAG, "get list of interfaces " + ifaces[0]);
for (String iface : ifaces) {
synchronized(this) {
if (mIface.equals(iface)) {
setInterfaceUp(iface);
break;
}
}
}
} catch (RemoteException e) {
Log.e(TAG, "Could not get list of interfaces " + e);
}
}
public void interfaceLinkStateChanged(String iface, boolean up) {
Log.d(TAG, "interfaceLinkStateChanged: iface = " + iface + ", up = " + up);
if (!mIface.equals(iface))
return;
if (mLinkUp == up)
return;
mLinkUp = up;
if (up) {
mHandler.removeMessages(EVENT_INTERFACE_LINK_STATE_CHANGED);
mHandler.sendMessageDelayed(mHandler.obtainMessage(EVENT_INTERFACE_LINK_STATE_CHANGED, 1, 0),
EVENT_INTERFACE_LINK_STATE_CHANGED_DELAY_MS);
} else {
mHandler.removeMessages(EVENT_INTERFACE_LINK_STATE_CHANGED);
mHandler.sendMessageDelayed(mHandler.obtainMessage(EVENT_INTERFACE_LINK_STATE_CHANGED, 0, 0),
0);
}
}
private class IpClientCallbacksImpl extends IpClientCallbacks {
private final ConditionVariable mIpClientStartCv = new ConditionVariable(false);
private final ConditionVariable mIpClientShutdownCv = new ConditionVariable(false);
@Override
public void onIpClientCreated(IIpClient ipClient) {
mIpClient = ipClient;
mIpClientStartCv.open();
}
private void awaitIpClientStart() {
mIpClientStartCv.block();
}
private void awaitIpClientShutdown() {
mIpClientShutdownCv.block();
}
@Override
public void onProvisioningSuccess(LinkProperties newLp) {
mLinkProperties = newLp;
onIpLayerStarted2(newLp);
}
@Override
public void onProvisioningFailure(LinkProperties newLp) {
mLinkProperties = newLp;
onIpLayerStopped2(newLp);
}
@Override
public void onLinkPropertiesChange(LinkProperties newLp) {
mLinkProperties = newLp;
}
@Override
public void onQuit() {