NetworkLogger.java revision dd9bb4fdd9f4b528734a7907d2bc92841ca648ab
1/*
2 * Copyright (C) 2016 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 *      http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17package com.android.server.devicepolicy;
18
19import android.content.pm.PackageManagerInternal;
20import android.net.IIpConnectivityMetrics;
21import android.net.INetdEventCallback;
22import android.os.RemoteException;
23import android.util.Log;
24import android.util.Slog;
25
26import com.android.server.ServiceThread;
27
28import java.util.ArrayList;
29import java.util.List;
30
31/**
32 * A class for managing network logging.
33 * This class is not thread-safe, callers should synchronize access.
34 */
35final class NetworkLogger {
36
37    private static final String TAG = NetworkLogger.class.getSimpleName();
38
39    private final DevicePolicyManagerService mDpm;
40    private final PackageManagerInternal mPm;
41
42    private IIpConnectivityMetrics mIpConnectivityMetrics;
43    private boolean mIsLoggingEnabled;
44
45    private final INetdEventCallback mNetdEventCallback = new INetdEventCallback.Stub() {
46        @Override
47        public void onDnsEvent(String hostname, String[] ipAddresses, int ipAddressesCount,
48                long timestamp, int uid) {
49            if (!mIsLoggingEnabled) {
50                return;
51            }
52            // TODO(mkarpinski): send msg with data to Handler
53        }
54
55        @Override
56        public void onConnectEvent(String ipAddr, int port, long timestamp, int uid) {
57            if (!mIsLoggingEnabled) {
58                return;
59            }
60            // TODO(mkarpinski): send msg with data to Handler
61        }
62    };
63
64    NetworkLogger(DevicePolicyManagerService dpm, PackageManagerInternal pm) {
65        mDpm = dpm;
66        mPm = pm;
67    }
68
69    private boolean checkIpConnectivityMetricsService() {
70        if (mIpConnectivityMetrics != null) {
71            return true;
72        }
73        final IIpConnectivityMetrics service = mDpm.mInjector.getIIpConnectivityMetrics();
74        if (service == null) {
75            return false;
76        }
77        mIpConnectivityMetrics = service;
78        return true;
79    }
80
81    boolean startNetworkLogging() {
82        Log.d(TAG, "Starting network logging.");
83        if (!checkIpConnectivityMetricsService()) {
84            // the IIpConnectivityMetrics service should have been present at this point
85            Slog.wtf(TAG, "Failed to register callback with IIpConnectivityMetrics.");
86            return false;
87        }
88        try {
89           if (mIpConnectivityMetrics.registerNetdEventCallback(mNetdEventCallback)) {
90                // TODO(mkarpinski): start a new ServiceThread, instantiate a Handler etc.
91                mIsLoggingEnabled = true;
92                return true;
93            } else {
94                return false;
95            }
96        } catch (RemoteException re) {
97            Slog.wtf(TAG, "Failed to make remote calls to register the callback", re);
98            return false;
99        }
100    }
101
102    boolean stopNetworkLogging() {
103        Log.d(TAG, "Stopping network logging");
104        // stop the logging regardless of whether we failed to unregister listener
105        mIsLoggingEnabled = false;
106        try {
107            if (!checkIpConnectivityMetricsService()) {
108                // the IIpConnectivityMetrics service should have been present at this point
109                Slog.wtf(TAG, "Failed to unregister callback with IIpConnectivityMetrics.");
110                // logging is forcefully disabled even if unregistering fails
111                return true;
112            }
113            return mIpConnectivityMetrics.unregisterNetdEventCallback();
114        } catch (RemoteException re) {
115            Slog.wtf(TAG, "Failed to make remote calls to unregister the callback", re);
116        } finally {
117            // TODO(mkarpinski): quitSafely() the Handler
118            return true;
119        }
120    }
121}
122