1/*
2 * Copyright (C) 2011 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 android.net;
18
19import static android.net.NetworkStats.ROAMING_ALL;
20import static android.net.NetworkStats.ROAMING_NO;
21import static android.net.NetworkStats.ROAMING_YES;
22import static android.net.NetworkStats.SET_DEFAULT;
23import static android.net.NetworkStats.SET_FOREGROUND;
24import static android.net.NetworkStats.SET_DBG_VPN_IN;
25import static android.net.NetworkStats.SET_DBG_VPN_OUT;
26import static android.net.NetworkStats.SET_ALL;
27import static android.net.NetworkStats.IFACE_ALL;
28import static android.net.NetworkStats.TAG_NONE;
29import static android.net.NetworkStats.UID_ALL;
30
31import android.test.suitebuilder.annotation.SmallTest;
32
33import com.google.android.collect.Sets;
34
35import junit.framework.TestCase;
36
37import java.util.HashSet;
38
39@SmallTest
40public class NetworkStatsTest extends TestCase {
41
42    private static final String TEST_IFACE = "test0";
43    private static final String TEST_IFACE2 = "test2";
44    private static final int TEST_UID = 1001;
45    private static final long TEST_START = 1194220800000L;
46
47    public void testFindIndex() throws Exception {
48        final NetworkStats stats = new NetworkStats(TEST_START, 4)
49                .addValues(TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, ROAMING_NO, 1024L, 8L, 0L,
50                        0L, 10)
51                .addValues(TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, ROAMING_NO, 0L, 0L, 1024L,
52                        8L, 11)
53                .addValues(TEST_IFACE, 102, SET_DEFAULT, TAG_NONE, ROAMING_NO, 1024L, 8L,
54                        1024L, 8L, 12)
55                .addValues(TEST_IFACE, 102, SET_DEFAULT, TAG_NONE, ROAMING_YES, 1024L, 8L,
56                        1024L, 8L, 12);
57
58        assertEquals(3, stats.findIndex(TEST_IFACE, 102, SET_DEFAULT, TAG_NONE, ROAMING_YES));
59        assertEquals(2, stats.findIndex(TEST_IFACE, 102, SET_DEFAULT, TAG_NONE, ROAMING_NO));
60        assertEquals(1, stats.findIndex(TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, ROAMING_NO));
61        assertEquals(0, stats.findIndex(TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, ROAMING_NO));
62        assertEquals(-1, stats.findIndex(TEST_IFACE, 6, SET_DEFAULT, TAG_NONE, ROAMING_NO));
63    }
64
65    public void testFindIndexHinted() {
66        final NetworkStats stats = new NetworkStats(TEST_START, 3)
67                .addValues(TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, ROAMING_NO, 1024L, 8L, 0L,
68                        0L, 10)
69                .addValues(TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, ROAMING_NO, 0L, 0L, 1024L,
70                        8L, 11)
71                .addValues(TEST_IFACE, 102, SET_DEFAULT, TAG_NONE, ROAMING_NO, 1024L, 8L,
72                        1024L, 8L, 12)
73                .addValues(TEST_IFACE2, 100, SET_FOREGROUND, TAG_NONE, ROAMING_NO, 1024L, 8L,
74                        0L, 0L, 10)
75                .addValues(TEST_IFACE2, 101, SET_DEFAULT, 0xF00D, ROAMING_NO, 0L, 0L, 1024L,
76                        8L, 11)
77                .addValues(TEST_IFACE2, 102, SET_DEFAULT, TAG_NONE, ROAMING_NO, 1024L, 8L,
78                        1024L, 8L, 12)
79                .addValues(TEST_IFACE2, 102, SET_DEFAULT, TAG_NONE, ROAMING_YES, 1024L, 8L,
80                        1024L, 8L, 12);
81
82        // verify that we correctly find across regardless of hinting
83        for (int hint = 0; hint < stats.size(); hint++) {
84            assertEquals(0, stats.findIndexHinted(TEST_IFACE, 100, SET_DEFAULT, TAG_NONE,
85                    ROAMING_NO, hint));
86            assertEquals(1, stats.findIndexHinted(TEST_IFACE, 101, SET_DEFAULT, TAG_NONE,
87                    ROAMING_NO, hint));
88            assertEquals(2, stats.findIndexHinted(TEST_IFACE, 102, SET_DEFAULT, TAG_NONE,
89                    ROAMING_NO, hint));
90            assertEquals(3, stats.findIndexHinted(TEST_IFACE2, 100, SET_FOREGROUND, TAG_NONE,
91                    ROAMING_NO, hint));
92            assertEquals(4, stats.findIndexHinted(TEST_IFACE2, 101, SET_DEFAULT, 0xF00D,
93                    ROAMING_NO, hint));
94            assertEquals(5, stats.findIndexHinted(TEST_IFACE2, 102, SET_DEFAULT, TAG_NONE,
95                    ROAMING_NO, hint));
96            assertEquals(6, stats.findIndexHinted(TEST_IFACE2, 102, SET_DEFAULT, TAG_NONE,
97                    ROAMING_YES, hint));
98            assertEquals(-1, stats.findIndexHinted(TEST_IFACE, 6, SET_DEFAULT, TAG_NONE,
99                    ROAMING_NO, hint));
100        }
101    }
102
103    public void testAddEntryGrow() throws Exception {
104        final NetworkStats stats = new NetworkStats(TEST_START, 3);
105
106        assertEquals(0, stats.size());
107        assertEquals(3, stats.internalSize());
108
109        stats.addValues(TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, ROAMING_NO, 1L, 1L, 2L,
110                2L, 3);
111        stats.addValues(TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, ROAMING_NO, 2L, 2L, 2L,
112                2L, 4);
113        stats.addValues(TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, ROAMING_YES, 3L, 3L, 2L,
114                2L, 5);
115
116        assertEquals(3, stats.size());
117        assertEquals(3, stats.internalSize());
118
119        stats.addValues(TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, ROAMING_NO, 4L, 40L, 4L,
120                40L, 7);
121        stats.addValues(TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, ROAMING_NO, 5L, 50L, 4L,
122                40L, 8);
123        stats.addValues(TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, ROAMING_NO, 6L, 60L, 5L,
124                50L, 10);
125        stats.addValues(TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, ROAMING_YES, 7L, 70L, 5L,
126                50L, 11);
127
128        assertEquals(7, stats.size());
129        assertTrue(stats.internalSize() >= 7);
130
131        assertValues(stats, 0, TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, ROAMING_NO, 1L, 1L,
132                2L, 2L, 3);
133        assertValues(stats, 1, TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, ROAMING_NO, 2L, 2L,
134                2L, 2L, 4);
135        assertValues(stats, 2, TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, ROAMING_YES, 3L, 3L,
136                2L, 2L, 5);
137        assertValues(stats, 3, TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, ROAMING_NO, 4L,
138                40L, 4L, 40L, 7);
139        assertValues(stats, 4, TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, ROAMING_NO, 5L,
140                50L, 4L, 40L, 8);
141        assertValues(stats, 5, TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, ROAMING_NO, 6L,
142                60L, 5L, 50L, 10);
143        assertValues(stats, 6, TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, ROAMING_YES, 7L,
144                70L, 5L, 50L, 11);
145    }
146
147    public void testCombineExisting() throws Exception {
148        final NetworkStats stats = new NetworkStats(TEST_START, 10);
149
150        stats.addValues(TEST_IFACE, 1001, SET_DEFAULT, TAG_NONE, 512L, 4L, 256L, 2L, 10);
151        stats.addValues(TEST_IFACE, 1001, SET_DEFAULT, 0xff, 128L, 1L, 128L, 1L, 2);
152        stats.combineValues(TEST_IFACE, 1001, SET_DEFAULT, TAG_NONE, -128L, -1L,
153                -128L, -1L, -1);
154
155        assertValues(stats, 0, TEST_IFACE, 1001, SET_DEFAULT, TAG_NONE, ROAMING_NO, 384L, 3L,
156                128L, 1L, 9);
157        assertValues(stats, 1, TEST_IFACE, 1001, SET_DEFAULT, 0xff, ROAMING_NO, 128L, 1L, 128L,
158                1L, 2);
159
160        // now try combining that should create row
161        stats.combineValues(TEST_IFACE, 5005, SET_DEFAULT, TAG_NONE, 128L, 1L,
162                128L, 1L, 3);
163        assertValues(stats, 2, TEST_IFACE, 5005, SET_DEFAULT, TAG_NONE, ROAMING_NO, 128L, 1L,
164                128L, 1L, 3);
165        stats.combineValues(TEST_IFACE, 5005, SET_DEFAULT, TAG_NONE, 128L, 1L,
166                128L, 1L, 3);
167        assertValues(stats, 2, TEST_IFACE, 5005, SET_DEFAULT, TAG_NONE, ROAMING_NO, 256L, 2L,
168                256L, 2L, 6);
169    }
170
171    public void testSubtractIdenticalData() throws Exception {
172        final NetworkStats before = new NetworkStats(TEST_START, 2)
173                .addValues(TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, 1024L, 8L, 0L, 0L, 11)
174                .addValues(TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, 0L, 0L, 1024L, 8L, 12);
175
176        final NetworkStats after = new NetworkStats(TEST_START, 2)
177                .addValues(TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, 1024L, 8L, 0L, 0L, 11)
178                .addValues(TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, 0L, 0L, 1024L, 8L, 12);
179
180        final NetworkStats result = after.subtract(before);
181
182        // identical data should result in zero delta
183        assertValues(result, 0, TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, ROAMING_NO, 0L, 0L, 0L,
184                0L, 0);
185        assertValues(result, 1, TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, ROAMING_NO, 0L, 0L, 0L,
186                0L, 0);
187    }
188
189    public void testSubtractIdenticalRows() throws Exception {
190        final NetworkStats before = new NetworkStats(TEST_START, 2)
191                .addValues(TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, 1024L, 8L, 0L, 0L, 11)
192                .addValues(TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, 0L, 0L, 1024L, 8L, 12);
193
194        final NetworkStats after = new NetworkStats(TEST_START, 2)
195                .addValues(TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, 1025L, 9L, 2L, 1L, 15)
196                .addValues(TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, 3L, 1L, 1028L, 9L, 20);
197
198        final NetworkStats result = after.subtract(before);
199
200        // expect delta between measurements
201        assertValues(result, 0, TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, ROAMING_NO, 1L, 1L, 2L,
202                1L, 4);
203        assertValues(result, 1, TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, ROAMING_NO, 3L, 1L, 4L,
204                1L, 8);
205    }
206
207    public void testSubtractNewRows() throws Exception {
208        final NetworkStats before = new NetworkStats(TEST_START, 2)
209                .addValues(TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, 1024L, 8L, 0L, 0L, 11)
210                .addValues(TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, 0L, 0L, 1024L, 8L, 12);
211
212        final NetworkStats after = new NetworkStats(TEST_START, 3)
213                .addValues(TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, 1024L, 8L, 0L, 0L, 11)
214                .addValues(TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, 0L, 0L, 1024L, 8L, 12)
215                .addValues(TEST_IFACE, 102, SET_DEFAULT, TAG_NONE, 1024L, 8L, 1024L, 8L, 20);
216
217        final NetworkStats result = after.subtract(before);
218
219        // its okay to have new rows
220        assertValues(result, 0, TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, ROAMING_NO, 0L, 0L, 0L,
221                0L, 0);
222        assertValues(result, 1, TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, ROAMING_NO, 0L, 0L, 0L,
223                0L, 0);
224        assertValues(result, 2, TEST_IFACE, 102, SET_DEFAULT, TAG_NONE, ROAMING_NO, 1024L, 8L,
225                1024L, 8L, 20);
226    }
227
228    public void testSubtractMissingRows() throws Exception {
229        final NetworkStats before = new NetworkStats(TEST_START, 2)
230                .addValues(TEST_IFACE, UID_ALL, SET_DEFAULT, TAG_NONE, 1024L, 0L, 0L, 0L, 0)
231                .addValues(TEST_IFACE2, UID_ALL, SET_DEFAULT, TAG_NONE, 2048L, 0L, 0L, 0L, 0);
232
233        final NetworkStats after = new NetworkStats(TEST_START, 1)
234                .addValues(TEST_IFACE2, UID_ALL, SET_DEFAULT, TAG_NONE, 2049L, 2L, 3L, 4L, 0);
235
236        final NetworkStats result = after.subtract(before);
237
238        // should silently drop omitted rows
239        assertEquals(1, result.size());
240        assertValues(result, 0, TEST_IFACE2, UID_ALL, SET_DEFAULT, TAG_NONE, ROAMING_NO, 1L,
241                2L, 3L, 4L, 0);
242        assertEquals(4L, result.getTotalBytes());
243    }
244
245    public void testTotalBytes() throws Exception {
246        final NetworkStats iface = new NetworkStats(TEST_START, 2)
247                .addValues(TEST_IFACE, UID_ALL, SET_DEFAULT, TAG_NONE, 128L, 0L, 0L, 0L, 0L)
248                .addValues(TEST_IFACE2, UID_ALL, SET_DEFAULT, TAG_NONE, 256L, 0L, 0L, 0L, 0L);
249        assertEquals(384L, iface.getTotalBytes());
250
251        final NetworkStats uidSet = new NetworkStats(TEST_START, 3)
252                .addValues(TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, 32L, 0L, 0L, 0L, 0L)
253                .addValues(TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, 32L, 0L, 0L, 0L, 0L)
254                .addValues(TEST_IFACE, 101, SET_FOREGROUND, TAG_NONE, 32L, 0L, 0L, 0L, 0L);
255        assertEquals(96L, uidSet.getTotalBytes());
256
257        final NetworkStats uidTag = new NetworkStats(TEST_START, 6)
258                .addValues(TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, 16L, 0L, 0L, 0L, 0L)
259                .addValues(TEST_IFACE2, 100, SET_DEFAULT, TAG_NONE, 16L, 0L, 0L, 0L, 0L)
260                .addValues(TEST_IFACE2, 100, SET_DEFAULT, 0xF00D, 8L, 0L, 0L, 0L, 0L)
261                .addValues(TEST_IFACE2, 100, SET_FOREGROUND, TAG_NONE, 16L, 0L, 0L, 0L, 0L)
262                .addValues(TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, 16L, 0L, 0L, 0L, 0L)
263                .addValues(TEST_IFACE, 101, SET_DEFAULT, 0xF00D, 8L, 0L, 0L, 0L, 0L);
264        assertEquals(64L, uidTag.getTotalBytes());
265
266        final NetworkStats uidRoaming = new NetworkStats(TEST_START, 3)
267                .addValues(TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, ROAMING_NO, 32L, 0L, 0L, 0L,
268                        0L)
269                .addValues(TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, ROAMING_NO, 32L, 0L, 0L, 0L,
270                        0L)
271                .addValues(TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, ROAMING_YES, 32L, 0L, 0L, 0L,
272                        0L);
273        assertEquals(96L, uidRoaming.getTotalBytes());
274    }
275
276    public void testGroupedByIfaceEmpty() throws Exception {
277        final NetworkStats uidStats = new NetworkStats(TEST_START, 3);
278        final NetworkStats grouped = uidStats.groupedByIface();
279
280        assertEquals(0, uidStats.size());
281        assertEquals(0, grouped.size());
282    }
283
284    public void testGroupedByIfaceAll() throws Exception {
285        final NetworkStats uidStats = new NetworkStats(TEST_START, 3)
286                .addValues(IFACE_ALL, 100, SET_ALL, TAG_NONE, ROAMING_NO, 128L, 8L, 0L, 2L,
287                        20L)
288                .addValues(IFACE_ALL, 101, SET_FOREGROUND, TAG_NONE, ROAMING_NO, 128L, 8L, 0L,
289                        2L, 20L)
290                .addValues(IFACE_ALL, 101, SET_ALL, TAG_NONE, ROAMING_YES, 128L, 8L, 0L, 2L,
291                        20L);
292        final NetworkStats grouped = uidStats.groupedByIface();
293
294        assertEquals(3, uidStats.size());
295        assertEquals(1, grouped.size());
296
297        assertValues(grouped, 0, IFACE_ALL, UID_ALL, SET_ALL, TAG_NONE, ROAMING_ALL, 384L, 24L, 0L,
298                6L, 0L);
299    }
300
301    public void testGroupedByIface() throws Exception {
302        final NetworkStats uidStats = new NetworkStats(TEST_START, 7)
303                .addValues(TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, ROAMING_NO, 128L, 8L, 0L,
304                        2L, 20L)
305                .addValues(TEST_IFACE2, 100, SET_DEFAULT, TAG_NONE, ROAMING_NO, 512L, 32L, 0L,
306                        0L, 0L)
307                .addValues(TEST_IFACE2, 100, SET_DEFAULT, 0xF00D, ROAMING_NO, 64L, 4L, 0L, 0L,
308                        0L)
309                .addValues(TEST_IFACE2, 100, SET_FOREGROUND, TAG_NONE, ROAMING_NO, 512L, 32L,
310                        0L, 0L, 0L)
311                .addValues(TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, ROAMING_NO, 128L, 8L, 0L,
312                        0L, 0L)
313                .addValues(TEST_IFACE, 101, SET_DEFAULT, 0xF00D, ROAMING_NO, 128L, 8L, 0L, 0L,
314                        0L)
315                .addValues(TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, ROAMING_YES, 128L, 8L, 0L,
316                        0L, 0L);
317
318        final NetworkStats grouped = uidStats.groupedByIface();
319
320        assertEquals(7, uidStats.size());
321
322        assertEquals(2, grouped.size());
323        assertValues(grouped, 0, TEST_IFACE, UID_ALL, SET_ALL, TAG_NONE, ROAMING_ALL, 384L, 24L, 0L,
324                2L, 0L);
325        assertValues(grouped, 1, TEST_IFACE2, UID_ALL, SET_ALL, TAG_NONE, ROAMING_ALL, 1024L, 64L,
326                0L, 0L, 0L);
327    }
328
329    public void testAddAllValues() {
330        final NetworkStats first = new NetworkStats(TEST_START, 5)
331                .addValues(TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, ROAMING_NO, 32L, 0L, 0L, 0L,
332                        0L)
333                .addValues(TEST_IFACE, 100, SET_FOREGROUND, TAG_NONE, ROAMING_NO, 32L, 0L, 0L,
334                        0L, 0L)
335                .addValues(TEST_IFACE, 100, SET_FOREGROUND, TAG_NONE, ROAMING_YES, 32L, 0L, 0L,
336                        0L, 0L);
337
338        final NetworkStats second = new NetworkStats(TEST_START, 2)
339                .addValues(TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, ROAMING_NO, 32L, 0L, 0L, 0L,
340                        0L)
341                .addValues(TEST_IFACE2, UID_ALL, SET_DEFAULT, TAG_NONE, ROAMING_NO, 32L, 0L,
342                        0L, 0L, 0L)
343                .addValues(TEST_IFACE, 100, SET_FOREGROUND, TAG_NONE, ROAMING_YES, 32L, 0L, 0L,
344                        0L, 0L);
345
346        first.combineAllValues(second);
347
348        assertEquals(4, first.size());
349        assertValues(first, 0, TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, ROAMING_NO, 64L, 0L, 0L,
350                0L, 0L);
351        assertValues(first, 1, TEST_IFACE, 100, SET_FOREGROUND, TAG_NONE, ROAMING_NO, 32L, 0L,
352                0L, 0L, 0L);
353        assertValues(first, 2, TEST_IFACE, 100, SET_FOREGROUND, TAG_NONE, ROAMING_YES, 64L, 0L,
354                0L, 0L, 0L);
355        assertValues(first, 3, TEST_IFACE2, UID_ALL, SET_DEFAULT, TAG_NONE, ROAMING_NO, 32L,
356                0L, 0L, 0L, 0L);
357    }
358
359    public void testGetTotal() {
360        final NetworkStats stats = new NetworkStats(TEST_START, 7)
361                .addValues(TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, ROAMING_NO, 128L, 8L, 0L,
362                        2L, 20L)
363                .addValues(TEST_IFACE2, 100, SET_DEFAULT, TAG_NONE, ROAMING_NO, 512L, 32L, 0L,
364                        0L, 0L)
365                .addValues(TEST_IFACE2, 100, SET_DEFAULT, 0xF00D, ROAMING_NO, 64L, 4L, 0L, 0L,
366                        0L)
367                .addValues(TEST_IFACE2, 100, SET_FOREGROUND, TAG_NONE, ROAMING_NO, 512L, 32L,
368                        0L, 0L, 0L)
369                .addValues(TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, ROAMING_NO, 128L, 8L, 0L,
370                        0L, 0L)
371                .addValues(TEST_IFACE, 101, SET_DEFAULT, 0xF00D, ROAMING_NO, 128L, 8L, 0L, 0L,
372                        0L)
373                .addValues(TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, ROAMING_YES, 128L, 8L, 0L,
374                        0L, 0L);
375
376        assertValues(stats.getTotal(null), 1408L, 88L, 0L, 2L, 20L);
377        assertValues(stats.getTotal(null, 100), 1280L, 80L, 0L, 2L, 20L);
378        assertValues(stats.getTotal(null, 101), 128L, 8L, 0L, 0L, 0L);
379
380        final HashSet<String> ifaces = Sets.newHashSet();
381        assertValues(stats.getTotal(null, ifaces), 0L, 0L, 0L, 0L, 0L);
382
383        ifaces.add(TEST_IFACE2);
384        assertValues(stats.getTotal(null, ifaces), 1024L, 64L, 0L, 0L, 0L);
385    }
386
387    public void testWithoutUid() throws Exception {
388        final NetworkStats before = new NetworkStats(TEST_START, 3)
389                .addValues(TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, 128L, 8L, 0L, 2L, 20L)
390                .addValues(TEST_IFACE2, 100, SET_DEFAULT, TAG_NONE, 512L, 32L, 0L, 0L, 0L)
391                .addValues(TEST_IFACE2, 100, SET_DEFAULT, 0xF00D, 64L, 4L, 0L, 0L, 0L)
392                .addValues(TEST_IFACE2, 100, SET_FOREGROUND, TAG_NONE, 512L, 32L, 0L, 0L, 0L)
393                .addValues(TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, 128L, 8L, 0L, 0L, 0L)
394                .addValues(TEST_IFACE, 101, SET_DEFAULT, 0xF00D, 128L, 8L, 0L, 0L, 0L);
395
396        final NetworkStats after = before.withoutUids(new int[] { 100 });
397        assertEquals(6, before.size());
398        assertEquals(2, after.size());
399        assertValues(after, 0, TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, ROAMING_NO, 128L, 8L,
400                0L, 0L, 0L);
401        assertValues(after, 1, TEST_IFACE, 101, SET_DEFAULT, 0xF00D, ROAMING_NO, 128L, 8L, 0L,
402                0L, 0L);
403    }
404
405    public void testClone() throws Exception {
406        final NetworkStats original = new NetworkStats(TEST_START, 5)
407                .addValues(TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, 128L, 8L, 0L, 2L, 20L)
408                .addValues(TEST_IFACE2, 100, SET_DEFAULT, TAG_NONE, 512L, 32L, 0L, 0L, 0L);
409
410        // make clone and mutate original
411        final NetworkStats clone = original.clone();
412        original.addValues(TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, 128L, 8L, 0L, 0L, 0L);
413
414        assertEquals(3, original.size());
415        assertEquals(2, clone.size());
416
417        assertEquals(128L + 512L + 128L, original.getTotalBytes());
418        assertEquals(128L + 512L, clone.getTotalBytes());
419    }
420
421    public void testAddWhenEmpty() throws Exception {
422        final NetworkStats red = new NetworkStats(TEST_START, -1);
423        final NetworkStats blue = new NetworkStats(TEST_START, 5)
424                .addValues(TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, 128L, 8L, 0L, 2L, 20L)
425                .addValues(TEST_IFACE2, 100, SET_DEFAULT, TAG_NONE, 512L, 32L, 0L, 0L, 0L);
426
427        // We're mostly checking that we don't crash
428        red.combineAllValues(blue);
429    }
430
431    public void testMigrateTun() throws Exception {
432        final int tunUid = 10030;
433        final String tunIface = "tun0";
434        final String underlyingIface = "wlan0";
435        final int testTag1 = 8888;
436        NetworkStats delta = new NetworkStats(TEST_START, 17)
437            .addValues(tunIface, 10100, SET_DEFAULT, TAG_NONE, 39605L, 46L, 12259L, 55L, 0L)
438            .addValues(tunIface, 10100, SET_FOREGROUND, TAG_NONE, 0L, 0L, 0L, 0L, 0L)
439            .addValues(tunIface, 10120, SET_DEFAULT, TAG_NONE, 72667L, 197L, 43909L, 241L, 0L)
440            .addValues(tunIface, 10120, SET_FOREGROUND, TAG_NONE, 9297L, 17L, 4128L, 21L, 0L)
441            // VPN package also uses some traffic through unprotected network.
442            .addValues(tunIface, tunUid, SET_DEFAULT, TAG_NONE, 4983L, 10L, 1801L, 12L, 0L)
443            .addValues(tunIface, tunUid, SET_FOREGROUND, TAG_NONE, 0L, 0L, 0L, 0L, 0L)
444            // Tag entries
445            .addValues(tunIface, 10120, SET_DEFAULT, testTag1, 21691L, 41L, 13820L, 51L, 0L)
446            .addValues(tunIface, 10120, SET_FOREGROUND, testTag1, 1281L, 2L, 665L, 2L, 0L)
447            // Irrelevant entries
448            .addValues(TEST_IFACE, 10100, SET_DEFAULT, TAG_NONE, 1685L, 5L, 2070L, 6L, 0L)
449            // Underlying Iface entries
450            .addValues(underlyingIface, 10100, SET_DEFAULT, TAG_NONE, 5178L, 8L, 2139L, 11L, 0L)
451            .addValues(underlyingIface, 10100, SET_FOREGROUND, TAG_NONE, 0L, 0L, 0L, 0L, 0L)
452            .addValues(underlyingIface, tunUid, SET_DEFAULT, TAG_NONE, 149873L, 287L,
453                    59217L /* smaller than sum(tun0) */, 299L /* smaller than sum(tun0) */, 0L)
454            .addValues(underlyingIface, tunUid, SET_FOREGROUND, TAG_NONE, 0L, 0L, 0L, 0L, 0L);
455
456        assertTrue(delta.migrateTun(tunUid, tunIface, underlyingIface));
457        assertEquals(21, delta.size());
458
459        // tunIface and TEST_IFACE entries are not changed.
460        assertValues(delta, 0, tunIface, 10100, SET_DEFAULT, TAG_NONE, ROAMING_NO,
461                39605L, 46L, 12259L, 55L, 0L);
462        assertValues(delta, 1, tunIface, 10100, SET_FOREGROUND, TAG_NONE, ROAMING_NO, 0L, 0L,
463                0L, 0L, 0L);
464        assertValues(delta, 2, tunIface, 10120, SET_DEFAULT, TAG_NONE, ROAMING_NO,
465                72667L, 197L, 43909L, 241L, 0L);
466        assertValues(delta, 3, tunIface, 10120, SET_FOREGROUND, TAG_NONE, ROAMING_NO,
467                9297L, 17L, 4128L, 21L, 0L);
468        assertValues(delta, 4, tunIface, tunUid, SET_DEFAULT, TAG_NONE, ROAMING_NO,
469                4983L, 10L, 1801L, 12L, 0L);
470        assertValues(delta, 5, tunIface, tunUid, SET_FOREGROUND, TAG_NONE, ROAMING_NO, 0L, 0L,
471                0L, 0L, 0L);
472        assertValues(delta, 6, tunIface, 10120, SET_DEFAULT, testTag1, ROAMING_NO,
473                21691L, 41L, 13820L, 51L, 0L);
474        assertValues(delta, 7, tunIface, 10120, SET_FOREGROUND, testTag1, ROAMING_NO, 1281L,
475                2L, 665L, 2L, 0L);
476        assertValues(delta, 8, TEST_IFACE, 10100, SET_DEFAULT, TAG_NONE, ROAMING_NO, 1685L, 5L,
477                2070L, 6L, 0L);
478
479        // Existing underlying Iface entries are updated
480        assertValues(delta, 9, underlyingIface, 10100, SET_DEFAULT, TAG_NONE, ROAMING_NO,
481                44783L, 54L, 13829L, 60L, 0L);
482        assertValues(delta, 10, underlyingIface, 10100, SET_FOREGROUND, TAG_NONE, ROAMING_NO,
483                0L, 0L, 0L, 0L, 0L);
484
485        // VPN underlying Iface entries are updated
486        assertValues(delta, 11, underlyingIface, tunUid, SET_DEFAULT, TAG_NONE, ROAMING_NO,
487                28304L, 27L, 1719L, 12L, 0L);
488        assertValues(delta, 12, underlyingIface, tunUid, SET_FOREGROUND, TAG_NONE, ROAMING_NO,
489                0L, 0L, 0L, 0L, 0L);
490
491        // New entries are added for new application's underlying Iface traffic
492        assertContains(delta, underlyingIface, 10120, SET_DEFAULT, TAG_NONE, ROAMING_NO,
493                72667L, 197L, 41872L, 219L, 0L);
494        assertContains(delta, underlyingIface, 10120, SET_FOREGROUND, TAG_NONE, ROAMING_NO,
495                9297L, 17L, 3936, 19L, 0L);
496        assertContains(delta, underlyingIface, 10120, SET_DEFAULT, testTag1, ROAMING_NO,
497                21691L, 41L, 13179L, 46L, 0L);
498        assertContains(delta, underlyingIface, 10120, SET_FOREGROUND, testTag1, ROAMING_NO,
499                1281L, 2L, 634L, 1L, 0L);
500
501        // New entries are added for debug purpose
502        assertContains(delta, underlyingIface, 10100, SET_DBG_VPN_IN, TAG_NONE, ROAMING_NO,
503                39605L, 46L, 11690, 49, 0);
504        assertContains(delta, underlyingIface, 10120, SET_DBG_VPN_IN, TAG_NONE, ROAMING_NO,
505                81964, 214, 45808, 238, 0);
506        assertContains(delta, underlyingIface, tunUid, SET_DBG_VPN_IN, TAG_NONE, ROAMING_NO,
507                4983, 10, 1717, 10, 0);
508        assertContains(delta, underlyingIface, tunUid, SET_DBG_VPN_OUT, TAG_NONE, ROAMING_ALL,
509                126552, 270, 59215, 297, 0);
510
511    }
512
513    private static void assertContains(NetworkStats stats,  String iface, int uid, int set,
514            int tag, int roaming, long rxBytes, long rxPackets, long txBytes, long txPackets,
515            long operations) {
516        int index = stats.findIndex(iface, uid, set, tag, roaming);
517        assertTrue(index != -1);
518        assertValues(stats, index, iface, uid, set, tag, roaming,
519                rxBytes, rxPackets, txBytes, txPackets, operations);
520    }
521
522    private static void assertValues(NetworkStats stats, int index, String iface, int uid, int set,
523            int tag, int roaming, long rxBytes, long rxPackets, long txBytes, long txPackets,
524            long operations) {
525        final NetworkStats.Entry entry = stats.getValues(index, null);
526        assertValues(entry, iface, uid, set, tag, roaming);
527        assertValues(entry, rxBytes, rxPackets, txBytes, txPackets, operations);
528    }
529
530    private static void assertValues(
531            NetworkStats.Entry entry, String iface, int uid, int set, int tag, int roaming) {
532        assertEquals(iface, entry.iface);
533        assertEquals(uid, entry.uid);
534        assertEquals(set, entry.set);
535        assertEquals(tag, entry.tag);
536        assertEquals(roaming, entry.roaming);
537    }
538
539    private static void assertValues(NetworkStats.Entry entry, long rxBytes, long rxPackets,
540            long txBytes, long txPackets, long operations) {
541        assertEquals(rxBytes, entry.rxBytes);
542        assertEquals(rxPackets, entry.rxPackets);
543        assertEquals(txBytes, entry.txBytes);
544        assertEquals(txPackets, entry.txPackets);
545        assertEquals(operations, entry.operations);
546    }
547
548}
549