1 /*
2  * Copyright (C) 2007 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 
17 package android.net;
18 
19 import android.annotation.SuppressLint;
20 import android.annotation.SystemApi;
21 import android.annotation.TestApi;
22 import android.app.DownloadManager;
23 import android.app.backup.BackupManager;
24 import android.app.usage.NetworkStatsManager;
25 import android.content.Context;
26 import android.media.MediaPlayer;
27 import android.os.RemoteException;
28 import android.os.ServiceManager;
29 import android.util.DataUnit;
30 
31 import com.android.server.NetworkManagementSocketTagger;
32 
33 import dalvik.system.SocketTagger;
34 
35 import java.io.FileDescriptor;
36 import java.io.IOException;
37 import java.net.DatagramSocket;
38 import java.net.Socket;
39 import java.net.SocketException;
40 
41 /**
42  * Class that provides network traffic statistics. These statistics include
43  * bytes transmitted and received and network packets transmitted and received,
44  * over all interfaces, over the mobile interface, and on a per-UID basis.
45  * <p>
46  * These statistics may not be available on all platforms. If the statistics are
47  * not supported by this device, {@link #UNSUPPORTED} will be returned.
48  * <p>
49  * Note that the statistics returned by this class reset and start from zero
50  * after every reboot. To access more robust historical network statistics data,
51  * use {@link NetworkStatsManager} instead.
52  */
53 public class TrafficStats {
54     /**
55      * The return value to indicate that the device does not support the statistic.
56      */
57     public final static int UNSUPPORTED = -1;
58 
59     /** @hide @deprecated use {@link DataUnit} instead to clarify SI-vs-IEC */
60     @Deprecated
61     public static final long KB_IN_BYTES = 1024;
62     /** @hide @deprecated use {@link DataUnit} instead to clarify SI-vs-IEC */
63     @Deprecated
64     public static final long MB_IN_BYTES = KB_IN_BYTES * 1024;
65     /** @hide @deprecated use {@link DataUnit} instead to clarify SI-vs-IEC */
66     @Deprecated
67     public static final long GB_IN_BYTES = MB_IN_BYTES * 1024;
68     /** @hide @deprecated use {@link DataUnit} instead to clarify SI-vs-IEC */
69     @Deprecated
70     public static final long TB_IN_BYTES = GB_IN_BYTES * 1024;
71     /** @hide @deprecated use {@link DataUnit} instead to clarify SI-vs-IEC */
72     @Deprecated
73     public static final long PB_IN_BYTES = TB_IN_BYTES * 1024;
74 
75     /**
76      * Special UID value used when collecting {@link NetworkStatsHistory} for
77      * removed applications.
78      *
79      * @hide
80      */
81     public static final int UID_REMOVED = -4;
82 
83     /**
84      * Special UID value used when collecting {@link NetworkStatsHistory} for
85      * tethering traffic.
86      *
87      * @hide
88      */
89     public static final int UID_TETHERING = -5;
90 
91     /**
92      * Default tag value for {@link DownloadManager} traffic.
93      *
94      * @hide
95      */
96     public static final int TAG_SYSTEM_DOWNLOAD = 0xFFFFFF01;
97 
98     /**
99      * Default tag value for {@link MediaPlayer} traffic.
100      *
101      * @hide
102      */
103     public static final int TAG_SYSTEM_MEDIA = 0xFFFFFF02;
104 
105     /**
106      * Default tag value for {@link BackupManager} backup traffic; that is,
107      * traffic from the device to the storage backend.
108      *
109      * @hide
110      */
111     public static final int TAG_SYSTEM_BACKUP = 0xFFFFFF03;
112 
113     /**
114      * Default tag value for {@link BackupManager} restore traffic; that is,
115      * app data retrieved from the storage backend at install time.
116      *
117      * @hide
118      */
119     public static final int TAG_SYSTEM_RESTORE = 0xFFFFFF04;
120 
121     /**
122      * Default tag value for code (typically APKs) downloaded by an app store on
123      * behalf of the app, such as updates.
124      *
125      * @hide
126      */
127     public static final int TAG_SYSTEM_APP = 0xFFFFFF05;
128 
129     /** @hide */
130     public static final int TAG_SYSTEM_DHCP = 0xFFFFFF40;
131     /** @hide */
132     public static final int TAG_SYSTEM_NTP = 0xFFFFFF41;
133     /** @hide */
134     public static final int TAG_SYSTEM_PROBE = 0xFFFFFF42;
135     /** @hide */
136     public static final int TAG_SYSTEM_NEIGHBOR = 0xFFFFFF43;
137     /** @hide */
138     public static final int TAG_SYSTEM_GPS = 0xFFFFFF44;
139     /** @hide */
140     public static final int TAG_SYSTEM_PAC = 0xFFFFFF45;
141 
142     private static INetworkStatsService sStatsService;
143 
getStatsService()144     private synchronized static INetworkStatsService getStatsService() {
145         if (sStatsService == null) {
146             sStatsService = INetworkStatsService.Stub.asInterface(
147                     ServiceManager.getService(Context.NETWORK_STATS_SERVICE));
148         }
149         return sStatsService;
150     }
151 
152     /**
153      * Snapshot of {@link NetworkStats} when the currently active profiling
154      * session started, or {@code null} if no session active.
155      *
156      * @see #startDataProfiling(Context)
157      * @see #stopDataProfiling(Context)
158      */
159     private static NetworkStats sActiveProfilingStart;
160 
161     private static Object sProfilingLock = new Object();
162 
163     private static final String LOOPBACK_IFACE = "lo";
164 
165     /**
166      * Set active tag to use when accounting {@link Socket} traffic originating
167      * from the current thread. Only one active tag per thread is supported.
168      * <p>
169      * Changes only take effect during subsequent calls to
170      * {@link #tagSocket(Socket)}.
171      * <p>
172      * Tags between {@code 0xFFFFFF00} and {@code 0xFFFFFFFF} are reserved and
173      * used internally by system services like {@link DownloadManager} when
174      * performing traffic on behalf of an application.
175      *
176      * @see #clearThreadStatsTag()
177      */
setThreadStatsTag(int tag)178     public static void setThreadStatsTag(int tag) {
179         NetworkManagementSocketTagger.setThreadSocketStatsTag(tag);
180     }
181 
182     /**
183      * Set active tag to use when accounting {@link Socket} traffic originating
184      * from the current thread. Only one active tag per thread is supported.
185      * <p>
186      * Changes only take effect during subsequent calls to
187      * {@link #tagSocket(Socket)}.
188      * <p>
189      * Tags between {@code 0xFFFFFF00} and {@code 0xFFFFFFFF} are reserved and
190      * used internally by system services like {@link DownloadManager} when
191      * performing traffic on behalf of an application.
192      *
193      * @return the current tag for the calling thread, which can be used to
194      *         restore any existing values after a nested operation is finished
195      */
getAndSetThreadStatsTag(int tag)196     public static int getAndSetThreadStatsTag(int tag) {
197         return NetworkManagementSocketTagger.setThreadSocketStatsTag(tag);
198     }
199 
200     /**
201      * Set active tag to use when accounting {@link Socket} traffic originating
202      * from the current thread. The tag used internally is well-defined to
203      * distinguish all backup-related traffic.
204      *
205      * @hide
206      */
207     @SystemApi
setThreadStatsTagBackup()208     public static void setThreadStatsTagBackup() {
209         setThreadStatsTag(TAG_SYSTEM_BACKUP);
210     }
211 
212     /**
213      * Set active tag to use when accounting {@link Socket} traffic originating
214      * from the current thread. The tag used internally is well-defined to
215      * distinguish all restore-related traffic.
216      *
217      * @hide
218      */
219     @SystemApi
setThreadStatsTagRestore()220     public static void setThreadStatsTagRestore() {
221         setThreadStatsTag(TAG_SYSTEM_RESTORE);
222     }
223 
224     /**
225      * Set active tag to use when accounting {@link Socket} traffic originating
226      * from the current thread. The tag used internally is well-defined to
227      * distinguish all code (typically APKs) downloaded by an app store on
228      * behalf of the app, such as updates.
229      *
230      * @hide
231      */
232     @SystemApi
setThreadStatsTagApp()233     public static void setThreadStatsTagApp() {
234         setThreadStatsTag(TAG_SYSTEM_APP);
235     }
236 
237     /**
238      * Get the active tag used when accounting {@link Socket} traffic originating
239      * from the current thread. Only one active tag per thread is supported.
240      * {@link #tagSocket(Socket)}.
241      *
242      * @see #setThreadStatsTag(int)
243      */
getThreadStatsTag()244     public static int getThreadStatsTag() {
245         return NetworkManagementSocketTagger.getThreadSocketStatsTag();
246     }
247 
248     /**
249      * Clear any active tag set to account {@link Socket} traffic originating
250      * from the current thread.
251      *
252      * @see #setThreadStatsTag(int)
253      */
clearThreadStatsTag()254     public static void clearThreadStatsTag() {
255         NetworkManagementSocketTagger.setThreadSocketStatsTag(-1);
256     }
257 
258     /**
259      * Set specific UID to use when accounting {@link Socket} traffic
260      * originating from the current thread. Designed for use when performing an
261      * operation on behalf of another application, or when another application
262      * is performing operations on your behalf.
263      * <p>
264      * Any app can <em>accept</em> blame for traffic performed on a socket
265      * originally created by another app by calling this method with the
266      * {@link android.system.Os#getuid()} value. However, only apps holding the
267      * {@code android.Manifest.permission#UPDATE_DEVICE_STATS} permission may
268      * <em>assign</em> blame to another UIDs.
269      * <p>
270      * Changes only take effect during subsequent calls to
271      * {@link #tagSocket(Socket)}.
272      */
273     @SystemApi
274     @SuppressLint("Doclava125")
setThreadStatsUid(int uid)275     public static void setThreadStatsUid(int uid) {
276         NetworkManagementSocketTagger.setThreadSocketStatsUid(uid);
277     }
278 
279     /**
280      * Get the active UID used when accounting {@link Socket} traffic originating
281      * from the current thread. Only one active tag per thread is supported.
282      * {@link #tagSocket(Socket)}.
283      *
284      * @see #setThreadStatsUid(int)
285      */
getThreadStatsUid()286     public static int getThreadStatsUid() {
287         return NetworkManagementSocketTagger.getThreadSocketStatsUid();
288     }
289 
290     /**
291      * Set specific UID to use when accounting {@link Socket} traffic
292      * originating from the current thread as the calling UID. Designed for use
293      * when another application is performing operations on your behalf.
294      * <p>
295      * Changes only take effect during subsequent calls to
296      * {@link #tagSocket(Socket)}.
297      *
298      * @removed
299      * @deprecated use {@link #setThreadStatsUid(int)} instead.
300      */
301     @Deprecated
setThreadStatsUidSelf()302     public static void setThreadStatsUidSelf() {
303         setThreadStatsUid(android.os.Process.myUid());
304     }
305 
306     /**
307      * Clear any active UID set to account {@link Socket} traffic originating
308      * from the current thread.
309      *
310      * @see #setThreadStatsUid(int)
311      */
312     @SystemApi
313     @SuppressLint("Doclava125")
clearThreadStatsUid()314     public static void clearThreadStatsUid() {
315         NetworkManagementSocketTagger.setThreadSocketStatsUid(-1);
316     }
317 
318     /**
319      * Tag the given {@link Socket} with any statistics parameters active for
320      * the current thread. Subsequent calls always replace any existing
321      * parameters. When finished, call {@link #untagSocket(Socket)} to remove
322      * statistics parameters.
323      *
324      * @see #setThreadStatsTag(int)
325      */
tagSocket(Socket socket)326     public static void tagSocket(Socket socket) throws SocketException {
327         SocketTagger.get().tag(socket);
328     }
329 
330     /**
331      * Remove any statistics parameters from the given {@link Socket}.
332      */
untagSocket(Socket socket)333     public static void untagSocket(Socket socket) throws SocketException {
334         SocketTagger.get().untag(socket);
335     }
336 
337     /**
338      * Tag the given {@link DatagramSocket} with any statistics parameters
339      * active for the current thread. Subsequent calls always replace any
340      * existing parameters. When finished, call
341      * {@link #untagDatagramSocket(DatagramSocket)} to remove statistics
342      * parameters.
343      *
344      * @see #setThreadStatsTag(int)
345      */
tagDatagramSocket(DatagramSocket socket)346     public static void tagDatagramSocket(DatagramSocket socket) throws SocketException {
347         SocketTagger.get().tag(socket);
348     }
349 
350     /**
351      * Remove any statistics parameters from the given {@link DatagramSocket}.
352      */
untagDatagramSocket(DatagramSocket socket)353     public static void untagDatagramSocket(DatagramSocket socket) throws SocketException {
354         SocketTagger.get().untag(socket);
355     }
356 
357     /**
358      * Tag the given {@link FileDescriptor} socket with any statistics
359      * parameters active for the current thread. Subsequent calls always replace
360      * any existing parameters. When finished, call
361      * {@link #untagFileDescriptor(FileDescriptor)} to remove statistics
362      * parameters.
363      *
364      * @see #setThreadStatsTag(int)
365      */
tagFileDescriptor(FileDescriptor fd)366     public static void tagFileDescriptor(FileDescriptor fd) throws IOException {
367         SocketTagger.get().tag(fd);
368     }
369 
370     /**
371      * Remove any statistics parameters from the given {@link FileDescriptor}
372      * socket.
373      */
untagFileDescriptor(FileDescriptor fd)374     public static void untagFileDescriptor(FileDescriptor fd) throws IOException {
375         SocketTagger.get().untag(fd);
376     }
377 
378     /**
379      * Start profiling data usage for current UID. Only one profiling session
380      * can be active at a time.
381      *
382      * @hide
383      */
startDataProfiling(Context context)384     public static void startDataProfiling(Context context) {
385         synchronized (sProfilingLock) {
386             if (sActiveProfilingStart != null) {
387                 throw new IllegalStateException("already profiling data");
388             }
389 
390             // take snapshot in time; we calculate delta later
391             sActiveProfilingStart = getDataLayerSnapshotForUid(context);
392         }
393     }
394 
395     /**
396      * Stop profiling data usage for current UID.
397      *
398      * @return Detailed {@link NetworkStats} of data that occurred since last
399      *         {@link #startDataProfiling(Context)} call.
400      * @hide
401      */
stopDataProfiling(Context context)402     public static NetworkStats stopDataProfiling(Context context) {
403         synchronized (sProfilingLock) {
404             if (sActiveProfilingStart == null) {
405                 throw new IllegalStateException("not profiling data");
406             }
407 
408             // subtract starting values and return delta
409             final NetworkStats profilingStop = getDataLayerSnapshotForUid(context);
410             final NetworkStats profilingDelta = NetworkStats.subtract(
411                     profilingStop, sActiveProfilingStart, null, null);
412             sActiveProfilingStart = null;
413             return profilingDelta;
414         }
415     }
416 
417     /**
418      * Increment count of network operations performed under the accounting tag
419      * currently active on the calling thread. This can be used to derive
420      * bytes-per-operation.
421      *
422      * @param operationCount Number of operations to increment count by.
423      */
incrementOperationCount(int operationCount)424     public static void incrementOperationCount(int operationCount) {
425         final int tag = getThreadStatsTag();
426         incrementOperationCount(tag, operationCount);
427     }
428 
429     /**
430      * Increment count of network operations performed under the given
431      * accounting tag. This can be used to derive bytes-per-operation.
432      *
433      * @param tag Accounting tag used in {@link #setThreadStatsTag(int)}.
434      * @param operationCount Number of operations to increment count by.
435      */
incrementOperationCount(int tag, int operationCount)436     public static void incrementOperationCount(int tag, int operationCount) {
437         final int uid = android.os.Process.myUid();
438         try {
439             getStatsService().incrementOperationCount(uid, tag, operationCount);
440         } catch (RemoteException e) {
441             throw e.rethrowFromSystemServer();
442         }
443     }
444 
445     /** {@hide} */
closeQuietly(INetworkStatsSession session)446     public static void closeQuietly(INetworkStatsSession session) {
447         // TODO: move to NetworkStatsService once it exists
448         if (session != null) {
449             try {
450                 session.close();
451             } catch (RuntimeException rethrown) {
452                 throw rethrown;
453             } catch (Exception ignored) {
454             }
455         }
456     }
457 
addIfSupported(long stat)458     private static long addIfSupported(long stat) {
459         return (stat == UNSUPPORTED) ? 0 : stat;
460     }
461 
462     /**
463      * Return number of packets transmitted across mobile networks since device
464      * boot. Counts packets across all mobile network interfaces, and always
465      * increases monotonically since device boot. Statistics are measured at the
466      * network layer, so they include both TCP and UDP usage.
467      * <p>
468      * Before {@link android.os.Build.VERSION_CODES#JELLY_BEAN_MR2}, this may
469      * return {@link #UNSUPPORTED} on devices where statistics aren't available.
470      */
getMobileTxPackets()471     public static long getMobileTxPackets() {
472         long total = 0;
473         for (String iface : getMobileIfaces()) {
474             total += addIfSupported(getTxPackets(iface));
475         }
476         return total;
477     }
478 
479     /**
480      * Return number of packets received across mobile networks since device
481      * boot. Counts packets across all mobile network interfaces, and always
482      * increases monotonically since device boot. Statistics are measured at the
483      * network layer, so they include both TCP and UDP usage.
484      * <p>
485      * Before {@link android.os.Build.VERSION_CODES#JELLY_BEAN_MR2}, this may
486      * return {@link #UNSUPPORTED} on devices where statistics aren't available.
487      */
getMobileRxPackets()488     public static long getMobileRxPackets() {
489         long total = 0;
490         for (String iface : getMobileIfaces()) {
491             total += addIfSupported(getRxPackets(iface));
492         }
493         return total;
494     }
495 
496     /**
497      * Return number of bytes transmitted across mobile networks since device
498      * boot. Counts packets across all mobile network interfaces, and always
499      * increases monotonically since device boot. Statistics are measured at the
500      * network layer, so they include both TCP and UDP usage.
501      * <p>
502      * Before {@link android.os.Build.VERSION_CODES#JELLY_BEAN_MR2}, this may
503      * return {@link #UNSUPPORTED} on devices where statistics aren't available.
504      */
getMobileTxBytes()505     public static long getMobileTxBytes() {
506         long total = 0;
507         for (String iface : getMobileIfaces()) {
508             total += addIfSupported(getTxBytes(iface));
509         }
510         return total;
511     }
512 
513     /**
514      * Return number of bytes received across mobile networks since device boot.
515      * Counts packets across all mobile network interfaces, and always increases
516      * monotonically since device boot. Statistics are measured at the network
517      * layer, so they include both TCP and UDP usage.
518      * <p>
519      * Before {@link android.os.Build.VERSION_CODES#JELLY_BEAN_MR2}, this may
520      * return {@link #UNSUPPORTED} on devices where statistics aren't available.
521      */
getMobileRxBytes()522     public static long getMobileRxBytes() {
523         long total = 0;
524         for (String iface : getMobileIfaces()) {
525             total += addIfSupported(getRxBytes(iface));
526         }
527         return total;
528     }
529 
530     /** {@hide} */
getMobileTcpRxPackets()531     public static long getMobileTcpRxPackets() {
532         long total = 0;
533         for (String iface : getMobileIfaces()) {
534             long stat = UNSUPPORTED;
535             try {
536                 stat = getStatsService().getIfaceStats(iface, TYPE_TCP_RX_PACKETS);
537             } catch (RemoteException e) {
538                 throw e.rethrowFromSystemServer();
539             }
540             total += addIfSupported(stat);
541         }
542         return total;
543     }
544 
545     /** {@hide} */
getMobileTcpTxPackets()546     public static long getMobileTcpTxPackets() {
547         long total = 0;
548         for (String iface : getMobileIfaces()) {
549             long stat = UNSUPPORTED;
550             try {
551                 stat = getStatsService().getIfaceStats(iface, TYPE_TCP_TX_PACKETS);
552             } catch (RemoteException e) {
553                 throw e.rethrowFromSystemServer();
554             }
555             total += addIfSupported(stat);
556         }
557         return total;
558     }
559 
560     /** {@hide} */
getTxPackets(String iface)561     public static long getTxPackets(String iface) {
562         try {
563             return getStatsService().getIfaceStats(iface, TYPE_TX_PACKETS);
564         } catch (RemoteException e) {
565             throw e.rethrowFromSystemServer();
566         }
567     }
568 
569     /** {@hide} */
getRxPackets(String iface)570     public static long getRxPackets(String iface) {
571         try {
572             return getStatsService().getIfaceStats(iface, TYPE_RX_PACKETS);
573         } catch (RemoteException e) {
574             throw e.rethrowFromSystemServer();
575         }
576     }
577 
578     /** {@hide} */
getTxBytes(String iface)579     public static long getTxBytes(String iface) {
580         try {
581             return getStatsService().getIfaceStats(iface, TYPE_TX_BYTES);
582         } catch (RemoteException e) {
583             throw e.rethrowFromSystemServer();
584         }
585     }
586 
587     /** {@hide} */
getRxBytes(String iface)588     public static long getRxBytes(String iface) {
589         try {
590             return getStatsService().getIfaceStats(iface, TYPE_RX_BYTES);
591         } catch (RemoteException e) {
592             throw e.rethrowFromSystemServer();
593         }
594     }
595 
596     /** {@hide} */
597     @TestApi
getLoopbackTxPackets()598     public static long getLoopbackTxPackets() {
599         try {
600             return getStatsService().getIfaceStats(LOOPBACK_IFACE, TYPE_TX_PACKETS);
601         } catch (RemoteException e) {
602             throw e.rethrowFromSystemServer();
603         }
604     }
605 
606     /** {@hide} */
607     @TestApi
getLoopbackRxPackets()608     public static long getLoopbackRxPackets() {
609         try {
610             return getStatsService().getIfaceStats(LOOPBACK_IFACE, TYPE_RX_PACKETS);
611         } catch (RemoteException e) {
612             throw e.rethrowFromSystemServer();
613         }
614     }
615 
616     /** {@hide} */
617     @TestApi
getLoopbackTxBytes()618     public static long getLoopbackTxBytes() {
619         try {
620             return getStatsService().getIfaceStats(LOOPBACK_IFACE, TYPE_TX_BYTES);
621         } catch (RemoteException e) {
622             throw e.rethrowFromSystemServer();
623         }
624     }
625 
626     /** {@hide} */
627     @TestApi
getLoopbackRxBytes()628     public static long getLoopbackRxBytes() {
629         try {
630             return getStatsService().getIfaceStats(LOOPBACK_IFACE, TYPE_RX_BYTES);
631         } catch (RemoteException e) {
632             throw e.rethrowFromSystemServer();
633         }
634     }
635 
636     /**
637      * Return number of packets transmitted since device boot. Counts packets
638      * across all network interfaces, and always increases monotonically since
639      * device boot. Statistics are measured at the network layer, so they
640      * include both TCP and UDP usage.
641      * <p>
642      * Before {@link android.os.Build.VERSION_CODES#JELLY_BEAN_MR2}, this may
643      * return {@link #UNSUPPORTED} on devices where statistics aren't available.
644      */
getTotalTxPackets()645     public static long getTotalTxPackets() {
646         try {
647             return getStatsService().getTotalStats(TYPE_TX_PACKETS);
648         } catch (RemoteException e) {
649             throw e.rethrowFromSystemServer();
650         }
651     }
652 
653     /**
654      * Return number of packets received since device boot. Counts packets
655      * across all network interfaces, and always increases monotonically since
656      * device boot. Statistics are measured at the network layer, so they
657      * include both TCP and UDP usage.
658      * <p>
659      * Before {@link android.os.Build.VERSION_CODES#JELLY_BEAN_MR2}, this may
660      * return {@link #UNSUPPORTED} on devices where statistics aren't available.
661      */
getTotalRxPackets()662     public static long getTotalRxPackets() {
663         try {
664             return getStatsService().getTotalStats(TYPE_RX_PACKETS);
665         } catch (RemoteException e) {
666             throw e.rethrowFromSystemServer();
667         }
668     }
669 
670     /**
671      * Return number of bytes transmitted since device boot. Counts packets
672      * across all network interfaces, and always increases monotonically since
673      * device boot. Statistics are measured at the network layer, so they
674      * include both TCP and UDP usage.
675      * <p>
676      * Before {@link android.os.Build.VERSION_CODES#JELLY_BEAN_MR2}, this may
677      * return {@link #UNSUPPORTED} on devices where statistics aren't available.
678      */
getTotalTxBytes()679     public static long getTotalTxBytes() {
680         try {
681             return getStatsService().getTotalStats(TYPE_TX_BYTES);
682         } catch (RemoteException e) {
683             throw e.rethrowFromSystemServer();
684         }
685     }
686 
687     /**
688      * Return number of bytes received since device boot. Counts packets across
689      * all network interfaces, and always increases monotonically since device
690      * boot. Statistics are measured at the network layer, so they include both
691      * TCP and UDP usage.
692      * <p>
693      * Before {@link android.os.Build.VERSION_CODES#JELLY_BEAN_MR2}, this may
694      * return {@link #UNSUPPORTED} on devices where statistics aren't available.
695      */
getTotalRxBytes()696     public static long getTotalRxBytes() {
697         try {
698             return getStatsService().getTotalStats(TYPE_RX_BYTES);
699         } catch (RemoteException e) {
700             throw e.rethrowFromSystemServer();
701         }
702     }
703 
704     /**
705      * Return number of bytes transmitted by the given UID since device boot.
706      * Counts packets across all network interfaces, and always increases
707      * monotonically since device boot. Statistics are measured at the network
708      * layer, so they include both TCP and UDP usage.
709      * <p>
710      * Before {@link android.os.Build.VERSION_CODES#JELLY_BEAN_MR2}, this may
711      * return {@link #UNSUPPORTED} on devices where statistics aren't available.
712      * <p>
713      * Starting in {@link android.os.Build.VERSION_CODES#N} this will only
714      * report traffic statistics for the calling UID. It will return
715      * {@link #UNSUPPORTED} for all other UIDs for privacy reasons. To access
716      * historical network statistics belonging to other UIDs, use
717      * {@link NetworkStatsManager}.
718      *
719      * @see android.os.Process#myUid()
720      * @see android.content.pm.ApplicationInfo#uid
721      */
getUidTxBytes(int uid)722     public static long getUidTxBytes(int uid) {
723         // This isn't actually enforcing any security; it just returns the
724         // unsupported value. The real filtering is done at the kernel level.
725         final int callingUid = android.os.Process.myUid();
726         if (callingUid == android.os.Process.SYSTEM_UID || callingUid == uid) {
727             try {
728                 return getStatsService().getUidStats(uid, TYPE_TX_BYTES);
729             } catch (RemoteException e) {
730                 throw e.rethrowFromSystemServer();
731             }
732         } else {
733             return UNSUPPORTED;
734         }
735     }
736 
737     /**
738      * Return number of bytes received by the given UID since device boot.
739      * Counts packets across all network interfaces, and always increases
740      * monotonically since device boot. Statistics are measured at the network
741      * layer, so they include both TCP and UDP usage.
742      * <p>
743      * Before {@link android.os.Build.VERSION_CODES#JELLY_BEAN_MR2}, this may return
744      * {@link #UNSUPPORTED} on devices where statistics aren't available.
745      * <p>
746      * Starting in {@link android.os.Build.VERSION_CODES#N} this will only
747      * report traffic statistics for the calling UID. It will return
748      * {@link #UNSUPPORTED} for all other UIDs for privacy reasons. To access
749      * historical network statistics belonging to other UIDs, use
750      * {@link NetworkStatsManager}.
751      *
752      * @see android.os.Process#myUid()
753      * @see android.content.pm.ApplicationInfo#uid
754      */
getUidRxBytes(int uid)755     public static long getUidRxBytes(int uid) {
756         // This isn't actually enforcing any security; it just returns the
757         // unsupported value. The real filtering is done at the kernel level.
758         final int callingUid = android.os.Process.myUid();
759         if (callingUid == android.os.Process.SYSTEM_UID || callingUid == uid) {
760             try {
761                 return getStatsService().getUidStats(uid, TYPE_RX_BYTES);
762             } catch (RemoteException e) {
763                 throw e.rethrowFromSystemServer();
764             }
765         } else {
766             return UNSUPPORTED;
767         }
768     }
769 
770     /**
771      * Return number of packets transmitted by the given UID since device boot.
772      * Counts packets across all network interfaces, and always increases
773      * monotonically since device boot. Statistics are measured at the network
774      * layer, so they include both TCP and UDP usage.
775      * <p>
776      * Before {@link android.os.Build.VERSION_CODES#JELLY_BEAN_MR2}, this may return
777      * {@link #UNSUPPORTED} on devices where statistics aren't available.
778      * <p>
779      * Starting in {@link android.os.Build.VERSION_CODES#N} this will only
780      * report traffic statistics for the calling UID. It will return
781      * {@link #UNSUPPORTED} for all other UIDs for privacy reasons. To access
782      * historical network statistics belonging to other UIDs, use
783      * {@link NetworkStatsManager}.
784      *
785      * @see android.os.Process#myUid()
786      * @see android.content.pm.ApplicationInfo#uid
787      */
getUidTxPackets(int uid)788     public static long getUidTxPackets(int uid) {
789         // This isn't actually enforcing any security; it just returns the
790         // unsupported value. The real filtering is done at the kernel level.
791         final int callingUid = android.os.Process.myUid();
792         if (callingUid == android.os.Process.SYSTEM_UID || callingUid == uid) {
793             try {
794                 return getStatsService().getUidStats(uid, TYPE_TX_PACKETS);
795             } catch (RemoteException e) {
796                 throw e.rethrowFromSystemServer();
797             }
798         } else {
799             return UNSUPPORTED;
800         }
801     }
802 
803     /**
804      * Return number of packets received by the given UID since device boot.
805      * Counts packets across all network interfaces, and always increases
806      * monotonically since device boot. Statistics are measured at the network
807      * layer, so they include both TCP and UDP usage.
808      * <p>
809      * Before {@link android.os.Build.VERSION_CODES#JELLY_BEAN_MR2}, this may return
810      * {@link #UNSUPPORTED} on devices where statistics aren't available.
811      * <p>
812      * Starting in {@link android.os.Build.VERSION_CODES#N} this will only
813      * report traffic statistics for the calling UID. It will return
814      * {@link #UNSUPPORTED} for all other UIDs for privacy reasons. To access
815      * historical network statistics belonging to other UIDs, use
816      * {@link NetworkStatsManager}.
817      *
818      * @see android.os.Process#myUid()
819      * @see android.content.pm.ApplicationInfo#uid
820      */
getUidRxPackets(int uid)821     public static long getUidRxPackets(int uid) {
822         // This isn't actually enforcing any security; it just returns the
823         // unsupported value. The real filtering is done at the kernel level.
824         final int callingUid = android.os.Process.myUid();
825         if (callingUid == android.os.Process.SYSTEM_UID || callingUid == uid) {
826             try {
827                 return getStatsService().getUidStats(uid, TYPE_RX_PACKETS);
828             } catch (RemoteException e) {
829                 throw e.rethrowFromSystemServer();
830             }
831         } else {
832             return UNSUPPORTED;
833         }
834     }
835 
836     /**
837      * @deprecated Starting in {@link android.os.Build.VERSION_CODES#JELLY_BEAN_MR2},
838      *             transport layer statistics are no longer available, and will
839      *             always return {@link #UNSUPPORTED}.
840      * @see #getUidTxBytes(int)
841      */
842     @Deprecated
getUidTcpTxBytes(int uid)843     public static long getUidTcpTxBytes(int uid) {
844         return UNSUPPORTED;
845     }
846 
847     /**
848      * @deprecated Starting in {@link android.os.Build.VERSION_CODES#JELLY_BEAN_MR2},
849      *             transport layer statistics are no longer available, and will
850      *             always return {@link #UNSUPPORTED}.
851      * @see #getUidRxBytes(int)
852      */
853     @Deprecated
getUidTcpRxBytes(int uid)854     public static long getUidTcpRxBytes(int uid) {
855         return UNSUPPORTED;
856     }
857 
858     /**
859      * @deprecated Starting in {@link android.os.Build.VERSION_CODES#JELLY_BEAN_MR2},
860      *             transport layer statistics are no longer available, and will
861      *             always return {@link #UNSUPPORTED}.
862      * @see #getUidTxBytes(int)
863      */
864     @Deprecated
getUidUdpTxBytes(int uid)865     public static long getUidUdpTxBytes(int uid) {
866         return UNSUPPORTED;
867     }
868 
869     /**
870      * @deprecated Starting in {@link android.os.Build.VERSION_CODES#JELLY_BEAN_MR2},
871      *             transport layer statistics are no longer available, and will
872      *             always return {@link #UNSUPPORTED}.
873      * @see #getUidRxBytes(int)
874      */
875     @Deprecated
getUidUdpRxBytes(int uid)876     public static long getUidUdpRxBytes(int uid) {
877         return UNSUPPORTED;
878     }
879 
880     /**
881      * @deprecated Starting in {@link android.os.Build.VERSION_CODES#JELLY_BEAN_MR2},
882      *             transport layer statistics are no longer available, and will
883      *             always return {@link #UNSUPPORTED}.
884      * @see #getUidTxPackets(int)
885      */
886     @Deprecated
getUidTcpTxSegments(int uid)887     public static long getUidTcpTxSegments(int uid) {
888         return UNSUPPORTED;
889     }
890 
891     /**
892      * @deprecated Starting in {@link android.os.Build.VERSION_CODES#JELLY_BEAN_MR2},
893      *             transport layer statistics are no longer available, and will
894      *             always return {@link #UNSUPPORTED}.
895      * @see #getUidRxPackets(int)
896      */
897     @Deprecated
getUidTcpRxSegments(int uid)898     public static long getUidTcpRxSegments(int uid) {
899         return UNSUPPORTED;
900     }
901 
902     /**
903      * @deprecated Starting in {@link android.os.Build.VERSION_CODES#JELLY_BEAN_MR2},
904      *             transport layer statistics are no longer available, and will
905      *             always return {@link #UNSUPPORTED}.
906      * @see #getUidTxPackets(int)
907      */
908     @Deprecated
getUidUdpTxPackets(int uid)909     public static long getUidUdpTxPackets(int uid) {
910         return UNSUPPORTED;
911     }
912 
913     /**
914      * @deprecated Starting in {@link android.os.Build.VERSION_CODES#JELLY_BEAN_MR2},
915      *             transport layer statistics are no longer available, and will
916      *             always return {@link #UNSUPPORTED}.
917      * @see #getUidRxPackets(int)
918      */
919     @Deprecated
getUidUdpRxPackets(int uid)920     public static long getUidUdpRxPackets(int uid) {
921         return UNSUPPORTED;
922     }
923 
924     /**
925      * Return detailed {@link NetworkStats} for the current UID. Requires no
926      * special permission.
927      */
getDataLayerSnapshotForUid(Context context)928     private static NetworkStats getDataLayerSnapshotForUid(Context context) {
929         // TODO: take snapshot locally, since proc file is now visible
930         final int uid = android.os.Process.myUid();
931         try {
932             return getStatsService().getDataLayerSnapshotForUid(uid);
933         } catch (RemoteException e) {
934             throw e.rethrowFromSystemServer();
935         }
936     }
937 
938     /**
939      * Return set of any ifaces associated with mobile networks since boot.
940      * Interfaces are never removed from this list, so counters should always be
941      * monotonic.
942      */
getMobileIfaces()943     private static String[] getMobileIfaces() {
944         try {
945             return getStatsService().getMobileIfaces();
946         } catch (RemoteException e) {
947             throw e.rethrowFromSystemServer();
948         }
949     }
950 
951     // NOTE: keep these in sync with android_net_TrafficStats.cpp
952     private static final int TYPE_RX_BYTES = 0;
953     private static final int TYPE_RX_PACKETS = 1;
954     private static final int TYPE_TX_BYTES = 2;
955     private static final int TYPE_TX_PACKETS = 3;
956     private static final int TYPE_TCP_RX_PACKETS = 4;
957     private static final int TYPE_TCP_TX_PACKETS = 5;
958 }
959