Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 50a2f8ea authored by Jeff Sharkey's avatar Jeff Sharkey Committed by Android (Google) Code Review
Browse files

Merge "Read iface stats from single proc file."

parents b177b190 ae2c1810
Loading
Loading
Loading
Loading
+78 −4
Original line number Diff line number Diff line
@@ -21,8 +21,8 @@ import static android.Manifest.permission.MANAGE_NETWORK_POLICY;
import static android.net.NetworkStats.IFACE_ALL;
import static android.net.NetworkStats.SET_DEFAULT;
import static android.net.NetworkStats.TAG_NONE;
import static android.net.TrafficStats.UID_TETHERING;
import static android.net.NetworkStats.UID_ALL;
import static android.net.TrafficStats.UID_TETHERING;
import static android.provider.Settings.Secure.NETSTATS_ENABLED;
import static com.android.server.NetworkManagementSocketTagger.PROP_QTAGUID_ENABLED;
import static com.android.server.NetworkManagementSocketTagger.kernelToTag;
@@ -86,11 +86,15 @@ public class NetworkManagementService extends INetworkManagementService.Stub
    @Deprecated
    private final File mStatsUid;
    /** Path to {@code /proc/net/dev}. */
    @Deprecated
    private final File mStatsIface;
    /** Path to {@code /proc/net/xt_qtaguid/stats}. */
    private final File mStatsXtUid;
    /** Path to {@code /proc/net/xt_qtaguid/iface_stat}. */
    @Deprecated
    private final File mStatsXtIface;
    /** Path to {@code /proc/net/xt_qtaguid/iface_stat_all}. */
    private final File mStatsXtIfaceAll;
    /** Path to {@code /proc/net/xt_qtaguid/stats}. */
    private final File mStatsXtUid;

    /**
     * Name representing {@link #setGlobalAlert(long)} limit when delivered to
@@ -98,12 +102,17 @@ public class NetworkManagementService extends INetworkManagementService.Stub
     */
    public static final String LIMIT_GLOBAL_ALERT = "globalAlert";

    /** {@link #mStatsXtUid} headers. */
    /** {@link #mStatsXtUid} and {@link #mStatsXtIfaceAll} headers. */
    private static final String KEY_IDX = "idx";
    private static final String KEY_IFACE = "iface";
    private static final String KEY_ACTIVE = "active";
    private static final String KEY_UID = "uid_tag_int";
    private static final String KEY_COUNTER_SET = "cnt_set";
    private static final String KEY_TAG_HEX = "acct_tag_hex";
    private static final String KEY_SNAP_RX_BYTES = "snap_rx_bytes";
    private static final String KEY_SNAP_RX_PACKETS = "snap_rx_packets";
    private static final String KEY_SNAP_TX_BYTES = "snap_tx_bytes";
    private static final String KEY_SNAP_TX_PACKETS = "snap_tx_packets";
    private static final String KEY_RX_BYTES = "rx_bytes";
    private static final String KEY_RX_PACKETS = "rx_packets";
    private static final String KEY_TX_BYTES = "tx_bytes";
@@ -170,6 +179,7 @@ public class NetworkManagementService extends INetworkManagementService.Stub
        mStatsIface = new File(procRoot, "net/dev");
        mStatsXtUid = new File(procRoot, "net/xt_qtaguid/stats");
        mStatsXtIface = new File(procRoot, "net/xt_qtaguid/iface_stat");
        mStatsXtIfaceAll = new File(procRoot, "net/xt_qtaguid/iface_stat_all");

        if ("simulator".equals(SystemProperties.get("ro.product.device"))) {
            return;
@@ -1072,6 +1082,15 @@ public class NetworkManagementService extends INetworkManagementService.Stub
        mContext.enforceCallingOrSelfPermission(
                android.Manifest.permission.ACCESS_NETWORK_STATE, "NetworkManagementService");

        if (mBandwidthControlEnabled && mStatsXtIfaceAll.exists()) {
            return getNetworkStatsSummarySingleFile();
        } else {
            return getNetworkStatsSummaryMultipleFiles();
        }
    }

    @Deprecated
    private NetworkStats getNetworkStatsSummaryMultipleFiles() {
        final NetworkStats stats = new NetworkStats(SystemClock.elapsedRealtime(), 6);
        final NetworkStats.Entry entry = new NetworkStats.Entry();

@@ -1156,6 +1175,61 @@ public class NetworkManagementService extends INetworkManagementService.Stub
        return stats;
    }

    private NetworkStats getNetworkStatsSummarySingleFile() {
        final NetworkStats stats = new NetworkStats(SystemClock.elapsedRealtime(), 6);
        final NetworkStats.Entry entry = new NetworkStats.Entry();

        // TODO: read directly from proc once headers are added
        final ArrayList<String> keys = Lists.newArrayList(KEY_IFACE, KEY_ACTIVE, KEY_SNAP_RX_BYTES,
                KEY_SNAP_RX_PACKETS, KEY_SNAP_TX_BYTES, KEY_SNAP_TX_PACKETS, KEY_RX_BYTES,
                KEY_RX_PACKETS, KEY_TX_BYTES, KEY_TX_PACKETS);
        final ArrayList<String> values = Lists.newArrayList();
        final HashMap<String, String> parsed = Maps.newHashMap();

        BufferedReader reader = null;
        try {
            reader = new BufferedReader(new FileReader(mStatsXtIfaceAll));

            String line;
            while ((line = reader.readLine()) != null) {
                splitLine(line, values);
                parseLine(keys, values, parsed);

                entry.iface = parsed.get(KEY_IFACE);
                entry.uid = UID_ALL;
                entry.set = SET_DEFAULT;
                entry.tag = TAG_NONE;

                // always include snapshot values
                entry.rxBytes = getParsedLong(parsed, KEY_SNAP_RX_BYTES);
                entry.rxPackets = getParsedLong(parsed, KEY_SNAP_RX_PACKETS);
                entry.txBytes = getParsedLong(parsed, KEY_SNAP_TX_BYTES);
                entry.txPackets = getParsedLong(parsed, KEY_SNAP_TX_PACKETS);

                // fold in active numbers, but only when active
                final boolean active = getParsedInt(parsed, KEY_ACTIVE) != 0;
                if (active) {
                    entry.rxBytes += getParsedLong(parsed, KEY_RX_BYTES);
                    entry.rxPackets += getParsedLong(parsed, KEY_RX_PACKETS);
                    entry.txBytes += getParsedLong(parsed, KEY_TX_BYTES);
                    entry.txPackets += getParsedLong(parsed, KEY_TX_PACKETS);
                }

                stats.addValues(entry);
            }
        } catch (NullPointerException e) {
            throw new IllegalStateException("problem parsing stats: " + e);
        } catch (NumberFormatException e) {
            throw new IllegalStateException("problem parsing stats: " + e);
        } catch (IOException e) {
            throw new IllegalStateException("problem parsing stats: " + e);
        } finally {
            IoUtils.closeQuietly(reader);
        }

        return stats;
    }

    @Override
    public NetworkStats getNetworkStatsDetail() {
        mContext.enforceCallingOrSelfPermission(
+6 −0
Original line number Diff line number Diff line
rmnet3 1 0 0 0 0 20822 501 1149991 815
rmnet2 1 0 0 0 0 1594 15 1313 15
rmnet1 1 0 0 0 0 207398 458 166918 565
rmnet0 1 0 0 0 0 2112 24 700 10
test1 1 1 2 3 4 5 6 7 8
test2 0 1 2 3 4 5 6 7 8
+10 −0
Original line number Diff line number Diff line
@@ -159,6 +159,16 @@ public class NetworkManagementServiceTest extends AndroidTestCase {
        assertStatsEntry(stats, "rmnet0", 1000, SET_FOREGROUND, 0, 26033L, 30L, 1401L, 26L);
    }

    public void testNetworkStatsSingle() throws Exception {
        stageFile(R.raw.xt_qtaguid_iface_typical, new File(mTestProc, "net/xt_qtaguid/iface_stat_all"));

        final NetworkStats stats = mService.getNetworkStatsSummary();
        assertEquals(6, stats.size());
        assertStatsEntry(stats, "rmnet0", UID_ALL, SET_DEFAULT, TAG_NONE, 2112L, 24L, 700L, 10L);
        assertStatsEntry(stats, "test1", UID_ALL, SET_DEFAULT, TAG_NONE, 6L, 8L, 10L, 12L);
        assertStatsEntry(stats, "test2", UID_ALL, SET_DEFAULT, TAG_NONE, 1L, 2L, 3L, 4L);
    }

    /**
     * Copy a {@link Resources#openRawResource(int)} into {@link File} for
     * testing purposes.