| /* |
| * 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.content.pm.PackageManager; |
| import com.android.internal.util.IndentingPrintWriter; |
| import android.net.ConnectivityManager; |
| import android.net.IEthernetManager; |
| import android.net.IpConfiguration; |
| import android.net.IpConfiguration.IpAssignment; |
| import android.net.IpConfiguration.ProxySettings; |
| import android.net.LinkAddress; |
| import android.net.NetworkAgent; |
| import android.net.NetworkInfo; |
| import android.net.NetworkRequest; |
| import android.net.RouteInfo; |
| import android.net.StaticIpConfiguration; |
| import android.os.Binder; |
| import android.os.IBinder; |
| import android.os.Handler; |
| import android.os.HandlerThread; |
| import android.os.Looper; |
| import android.os.Message; |
| import android.os.Messenger; |
| import android.os.INetworkManagementService; |
| import android.os.RemoteException; |
| import android.os.ServiceManager; |
| import android.text.TextUtils; |
| import android.util.Log; |
| import android.util.PrintWriterPrinter; |
| |
| import java.io.FileDescriptor; |
| import java.io.PrintWriter; |
| import java.util.concurrent.atomic.AtomicBoolean; |
| |
| |
| /** |
| * EthernetServiceImpl handles remote Ethernet operation requests by implementing |
| * the IEthernetManager interface. |
| * |
| * @hide |
| */ |
| public class EthernetServiceImpl extends IEthernetManager.Stub { |
| private static final String TAG = "EthernetServiceImpl"; |
| |
| private final Context mContext; |
| private final EthernetConfigStore mEthernetConfigStore; |
| private final INetworkManagementService mNMService; |
| private final AtomicBoolean mStarted = new AtomicBoolean(false); |
| private IpConfiguration mIpConfiguration; |
| private ConnectivityManager mCM; |
| |
| private Handler mHandler; |
| private NetworkInfo mNetworkInfo; |
| private final EthernetNetworkFactory mTracker; |
| |
| public EthernetServiceImpl(Context context) { |
| mContext = context; |
| Log.i(TAG, "Creating EthernetConfigStore"); |
| mEthernetConfigStore = new EthernetConfigStore(); |
| mIpConfiguration = mEthernetConfigStore.readIpAndProxyConfigurations(); |
| |
| Log.i(TAG, "Read stored IP configuration: " + mIpConfiguration); |
| |
| IBinder b = ServiceManager.getService(Context.NETWORKMANAGEMENT_SERVICE); |
| mNMService = INetworkManagementService.Stub.asInterface(b); |
| |
| mTracker = new EthernetNetworkFactory(); |
| } |
| |
| private void enforceAccessPermission() { |
| mContext.enforceCallingOrSelfPermission( |
| android.Manifest.permission.ACCESS_NETWORK_STATE, |
| "EthernetService"); |
| } |
| |
| private void enforceChangePermission() { |
| mContext.enforceCallingOrSelfPermission( |
| android.Manifest.permission.CHANGE_NETWORK_STATE, |
| "EthernetService"); |
| } |
| |
| private void enforceConnectivityInternalPermission() { |
| mContext.enforceCallingOrSelfPermission( |
| android.Manifest.permission.CONNECTIVITY_INTERNAL, |
| "ConnectivityService"); |
| } |
| |
| public void start() { |
| Log.i(TAG, "Starting Ethernet service"); |
| mCM = (ConnectivityManager) mContext.getSystemService(Context.CONNECTIVITY_SERVICE); |
| |
| HandlerThread handlerThread = new HandlerThread("EthernetServiceThread"); |
| handlerThread.start(); |
| mHandler = new Handler(handlerThread.getLooper()); |
| |
| mTracker.start(mContext, mHandler); |
| |
| mStarted.set(true); |
| } |
| |
| /** |
| * Get Ethernet configuration |
| * @return the Ethernet Configuration, contained in {@link IpConfiguration}. |
| */ |
| public IpConfiguration getConfiguration() { |
| enforceAccessPermission(); |
| |
| synchronized (mIpConfiguration) { |
| return new IpConfiguration(mIpConfiguration); |
| } |
| } |
| |
| /** |
| * Set Ethernet configuration |
| */ |
| public void setConfiguration(IpConfiguration config) { |
| if (!mStarted.get()) { |
| Log.w(TAG, "System isn't ready enough to change ethernet configuration"); |
| } |
| |
| enforceChangePermission(); |
| enforceConnectivityInternalPermission(); |
| |
| 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 (!config.equals(mIpConfiguration)) { |
| mIpConfiguration = new IpConfiguration(config); |
| mTracker.stop(); |
| mTracker.start(mContext, mHandler); |
| } |
| } |
| } |
| |
| @Override |
| protected void dump(FileDescriptor fd, PrintWriter writer, String[] args) { |
| final IndentingPrintWriter pw = new IndentingPrintWriter(writer, " "); |
| if (mContext.checkCallingOrSelfPermission(android.Manifest.permission.DUMP) |
| != PackageManager.PERMISSION_GRANTED) { |
| pw.println("Permission Denial: can't dump EthernetService from pid=" |
| + Binder.getCallingPid() |
| + ", uid=" + Binder.getCallingUid()); |
| return; |
| } |
| |
| pw.println("Current Ethernet state: "); |
| pw.increaseIndent(); |
| mTracker.dump(fd, pw, args); |
| pw.decreaseIndent(); |
| |
| pw.println(); |
| pw.println("Stored Ethernet configuration: "); |
| pw.increaseIndent(); |
| pw.println(mIpConfiguration); |
| pw.decreaseIndent(); |
| |
| pw.println("Handler:"); |
| pw.increaseIndent(); |
| mHandler.dump(new PrintWriterPrinter(pw), "EthernetServiceImpl"); |
| pw.decreaseIndent(); |
| } |
| } |