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.app.DownloadManager; 20 import android.app.backup.BackupManager; 21 import android.content.Context; 22 import android.media.MediaPlayer; 23 import android.os.RemoteException; 24 import android.os.ServiceManager; 25 26 import com.android.server.NetworkManagementSocketTagger; 27 28 import dalvik.system.SocketTagger; 29 30 import java.net.Socket; 31 import java.net.SocketException; 32 33 /** 34 * Class that provides network traffic statistics. These statistics include 35 * bytes transmitted and received and network packets transmitted and received, 36 * over all interfaces, over the mobile interface, and on a per-UID basis. 37 * <p> 38 * These statistics may not be available on all platforms. If the statistics 39 * are not supported by this device, {@link #UNSUPPORTED} will be returned. 40 */ 41 public class TrafficStats { 42 /** 43 * The return value to indicate that the device does not support the statistic. 44 */ 45 public final static int UNSUPPORTED = -1; 46 47 /** 48 * Special UID value used when collecting {@link NetworkStatsHistory} for 49 * removed applications. 50 * 51 * @hide 52 */ 53 public static final int UID_REMOVED = -4; 54 55 /** 56 * Special UID value used when collecting {@link NetworkStatsHistory} for 57 * tethering traffic. 58 * 59 * @hide 60 */ 61 public static final int UID_TETHERING = -5; 62 63 /** 64 * Default tag value for {@link DownloadManager} traffic. 65 * 66 * @hide 67 */ 68 public static final int TAG_SYSTEM_DOWNLOAD = 0xFFFFFF01; 69 70 /** 71 * Default tag value for {@link MediaPlayer} traffic. 72 * 73 * @hide 74 */ 75 public static final int TAG_SYSTEM_MEDIA = 0xFFFFFF02; 76 77 /** 78 * Default tag value for {@link BackupManager} traffic. 79 * 80 * @hide 81 */ 82 public static final int TAG_SYSTEM_BACKUP = 0xFFFFFF03; 83 84 /** 85 * Snapshot of {@link NetworkStats} when the currently active profiling 86 * session started, or {@code null} if no session active. 87 * 88 * @see #startDataProfiling(Context) 89 * @see #stopDataProfiling(Context) 90 */ 91 private static NetworkStats sActiveProfilingStart; 92 93 private static Object sProfilingLock = new Object(); 94 95 /** 96 * Set active tag to use when accounting {@link Socket} traffic originating 97 * from the current thread. Only one active tag per thread is supported. 98 * <p> 99 * Changes only take effect during subsequent calls to 100 * {@link #tagSocket(Socket)}. 101 * <p> 102 * Tags between {@code 0xFFFFFF00} and {@code 0xFFFFFFFF} are reserved and 103 * used internally by system services like {@link DownloadManager} when 104 * performing traffic on behalf of an application. 105 */ 106 public static void setThreadStatsTag(int tag) { 107 NetworkManagementSocketTagger.setThreadSocketStatsTag(tag); 108 } 109 110 /** 111 * Get the active tag used when accounting {@link Socket} traffic originating 112 * from the current thread. Only one active tag per thread is supported. 113 * {@link #tagSocket(Socket)}. 114 */ 115 public static int getThreadStatsTag() { 116 return NetworkManagementSocketTagger.getThreadSocketStatsTag(); 117 } 118 119 public static void clearThreadStatsTag() { 120 NetworkManagementSocketTagger.setThreadSocketStatsTag(-1); 121 } 122 123 /** 124 * Set specific UID to use when accounting {@link Socket} traffic 125 * originating from the current thread. Designed for use when performing an 126 * operation on behalf of another application. 127 * <p> 128 * Changes only take effect during subsequent calls to 129 * {@link #tagSocket(Socket)}. 130 * <p> 131 * To take effect, caller must hold 132 * {@link android.Manifest.permission#UPDATE_DEVICE_STATS} permission. 133 * 134 * {@hide} 135 */ 136 public static void setThreadStatsUid(int uid) { 137 NetworkManagementSocketTagger.setThreadSocketStatsUid(uid); 138 } 139 140 /** {@hide} */ 141 public static void clearThreadStatsUid() { 142 NetworkManagementSocketTagger.setThreadSocketStatsUid(-1); 143 } 144 145 /** 146 * Tag the given {@link Socket} with any statistics parameters active for 147 * the current thread. Subsequent calls always replace any existing 148 * parameters. When finished, call {@link #untagSocket(Socket)} to remove 149 * statistics parameters. 150 * 151 * @see #setThreadStatsTag(int) 152 * @see #setThreadStatsUid(int) 153 */ 154 public static void tagSocket(Socket socket) throws SocketException { 155 SocketTagger.get().tag(socket); 156 } 157 158 /** 159 * Remove any statistics parameters from the given {@link Socket}. 160 */ 161 public static void untagSocket(Socket socket) throws SocketException { 162 SocketTagger.get().untag(socket); 163 } 164 165 /** 166 * Start profiling data usage for current UID. Only one profiling session 167 * can be active at a time. 168 * 169 * @hide 170 */ 171 public static void startDataProfiling(Context context) { 172 synchronized (sProfilingLock) { 173 if (sActiveProfilingStart != null) { 174 throw new IllegalStateException("already profiling data"); 175 } 176 177 // take snapshot in time; we calculate delta later 178 sActiveProfilingStart = getDataLayerSnapshotForUid(context); 179 } 180 } 181 182 /** 183 * Stop profiling data usage for current UID. 184 * 185 * @return Detailed {@link NetworkStats} of data that occurred since last 186 * {@link #startDataProfiling(Context)} call. 187 * @hide 188 */ 189 public static NetworkStats stopDataProfiling(Context context) { 190 synchronized (sProfilingLock) { 191 if (sActiveProfilingStart == null) { 192 throw new IllegalStateException("not profiling data"); 193 } 194 195 // subtract starting values and return delta 196 final NetworkStats profilingStop = getDataLayerSnapshotForUid(context); 197 final NetworkStats profilingDelta = profilingStop.subtractClamped( 198 sActiveProfilingStart); 199 sActiveProfilingStart = null; 200 return profilingDelta; 201 } 202 } 203 204 /** 205 * Increment count of network operations performed under the accounting tag 206 * currently active on the calling thread. This can be used to derive 207 * bytes-per-operation. 208 * 209 * @param operationCount Number of operations to increment count by. 210 */ 211 public static void incrementOperationCount(int operationCount) { 212 final int tag = getThreadStatsTag(); 213 incrementOperationCount(tag, operationCount); 214 } 215 216 /** 217 * Increment count of network operations performed under the given 218 * accounting tag. This can be used to derive bytes-per-operation. 219 * 220 * @param tag Accounting tag used in {@link #setThreadStatsTag(int)}. 221 * @param operationCount Number of operations to increment count by. 222 */ 223 public static void incrementOperationCount(int tag, int operationCount) { 224 final INetworkStatsService statsService = INetworkStatsService.Stub.asInterface( 225 ServiceManager.getService(Context.NETWORK_STATS_SERVICE)); 226 final int uid = android.os.Process.myUid(); 227 try { 228 statsService.incrementOperationCount(uid, tag, operationCount); 229 } catch (RemoteException e) { 230 throw new RuntimeException(e); 231 } 232 } 233 234 /** 235 * Get the total number of packets transmitted through the mobile interface. 236 * 237 * @return number of packets. If the statistics are not supported by this device, 238 * {@link #UNSUPPORTED} will be returned. 239 */ 240 public static native long getMobileTxPackets(); 241 242 /** 243 * Get the total number of packets received through the mobile interface. 244 * 245 * @return number of packets. If the statistics are not supported by this device, 246 * {@link #UNSUPPORTED} will be returned. 247 */ 248 public static native long getMobileRxPackets(); 249 250 /** 251 * Get the total number of bytes transmitted through the mobile interface. 252 * 253 * @return number of bytes. If the statistics are not supported by this device, 254 * {@link #UNSUPPORTED} will be returned. 255 */ 256 public static native long getMobileTxBytes(); 257 258 /** 259 * Get the total number of bytes received through the mobile interface. 260 * 261 * @return number of bytes. If the statistics are not supported by this device, 262 * {@link #UNSUPPORTED} will be returned. 263 */ 264 public static native long getMobileRxBytes(); 265 266 /** 267 * Get the total number of packets transmitted through the specified interface. 268 * 269 * @return number of packets. If the statistics are not supported by this interface, 270 * {@link #UNSUPPORTED} will be returned. 271 * @hide 272 */ 273 public static native long getTxPackets(String iface); 274 275 /** 276 * Get the total number of packets received through the specified interface. 277 * 278 * @return number of packets. If the statistics are not supported by this interface, 279 * {@link #UNSUPPORTED} will be returned. 280 * @hide 281 */ 282 public static native long getRxPackets(String iface); 283 284 /** 285 * Get the total number of bytes transmitted through the specified interface. 286 * 287 * @return number of bytes. If the statistics are not supported by this interface, 288 * {@link #UNSUPPORTED} will be returned. 289 * @hide 290 */ 291 public static native long getTxBytes(String iface); 292 293 /** 294 * Get the total number of bytes received through the specified interface. 295 * 296 * @return number of bytes. If the statistics are not supported by this interface, 297 * {@link #UNSUPPORTED} will be returned. 298 * @hide 299 */ 300 public static native long getRxBytes(String iface); 301 302 303 /** 304 * Get the total number of packets sent through all network interfaces. 305 * 306 * @return the number of packets. If the statistics are not supported by this device, 307 * {@link #UNSUPPORTED} will be returned. 308 */ 309 public static native long getTotalTxPackets(); 310 311 /** 312 * Get the total number of packets received through all network interfaces. 313 * 314 * @return number of packets. If the statistics are not supported by this device, 315 * {@link #UNSUPPORTED} will be returned. 316 */ 317 public static native long getTotalRxPackets(); 318 319 /** 320 * Get the total number of bytes sent through all network interfaces. 321 * 322 * @return number of bytes. If the statistics are not supported by this device, 323 * {@link #UNSUPPORTED} will be returned. 324 */ 325 public static native long getTotalTxBytes(); 326 327 /** 328 * Get the total number of bytes received through all network interfaces. 329 * 330 * @return number of bytes. If the statistics are not supported by this device, 331 * {@link #UNSUPPORTED} will be returned. 332 */ 333 public static native long getTotalRxBytes(); 334 335 /** 336 * Get the number of bytes sent through the network for this UID. 337 * The statistics are across all interfaces. 338 * 339 * {@see android.os.Process#myUid()}. 340 * 341 * @param uid The UID of the process to examine. 342 * @return number of bytes. If the statistics are not supported by this device, 343 * {@link #UNSUPPORTED} will be returned. 344 */ 345 public static native long getUidTxBytes(int uid); 346 347 /** 348 * Get the number of bytes received through the network for this UID. 349 * The statistics are across all interfaces. 350 * 351 * {@see android.os.Process#myUid()}. 352 * 353 * @param uid The UID of the process to examine. 354 * @return number of bytes 355 */ 356 public static native long getUidRxBytes(int uid); 357 358 /** 359 * Get the number of packets (TCP segments + UDP) sent through 360 * the network for this UID. 361 * The statistics are across all interfaces. 362 * 363 * {@see android.os.Process#myUid()}. 364 * 365 * @param uid The UID of the process to examine. 366 * @return number of packets. 367 * If the statistics are not supported by this device, 368 * {@link #UNSUPPORTED} will be returned. 369 */ 370 public static native long getUidTxPackets(int uid); 371 372 /** 373 * Get the number of packets (TCP segments + UDP) received through 374 * the network for this UID. 375 * The statistics are across all interfaces. 376 * 377 * {@see android.os.Process#myUid()}. 378 * 379 * @param uid The UID of the process to examine. 380 * @return number of packets 381 */ 382 public static native long getUidRxPackets(int uid); 383 384 /** 385 * Get the number of TCP payload bytes sent for this UID. 386 * This total does not include protocol and control overheads at 387 * the transport and the lower layers of the networking stack. 388 * The statistics are across all interfaces. 389 * 390 * {@see android.os.Process#myUid()}. 391 * 392 * @param uid The UID of the process to examine. 393 * @return number of bytes. If the statistics are not supported by this device, 394 * {@link #UNSUPPORTED} will be returned. 395 */ 396 public static native long getUidTcpTxBytes(int uid); 397 398 /** 399 * Get the number of TCP payload bytes received for this UID. 400 * This total does not include protocol and control overheads at 401 * the transport and the lower layers of the networking stack. 402 * The statistics are across all interfaces. 403 * 404 * {@see android.os.Process#myUid()}. 405 * 406 * @param uid The UID of the process to examine. 407 * @return number of bytes. If the statistics are not supported by this device, 408 * {@link #UNSUPPORTED} will be returned. 409 */ 410 public static native long getUidTcpRxBytes(int uid); 411 412 /** 413 * Get the number of UDP payload bytes sent for this UID. 414 * This total does not include protocol and control overheads at 415 * the transport and the lower layers of the networking stack. 416 * The statistics are across all interfaces. 417 * 418 * {@see android.os.Process#myUid()}. 419 * 420 * @param uid The UID of the process to examine. 421 * @return number of bytes. If the statistics are not supported by this device, 422 * {@link #UNSUPPORTED} will be returned. 423 */ 424 public static native long getUidUdpTxBytes(int uid); 425 426 /** 427 * Get the number of UDP payload bytes received for this UID. 428 * This total does not include protocol and control overheads at 429 * the transport and the lower layers of the networking stack. 430 * The statistics are across all interfaces. 431 * 432 * {@see android.os.Process#myUid()}. 433 * 434 * @param uid The UID of the process to examine. 435 * @return number of bytes. If the statistics are not supported by this device, 436 * {@link #UNSUPPORTED} will be returned. 437 */ 438 public static native long getUidUdpRxBytes(int uid); 439 440 /** 441 * Get the number of TCP segments sent for this UID. 442 * Does not include TCP control packets (SYN/ACKs/FIN/..). 443 * The statistics are across all interfaces. 444 * 445 * {@see android.os.Process#myUid()}. 446 * 447 * @param uid The UID of the process to examine. 448 * @return number of TCP segments. If the statistics are not supported by this device, 449 * {@link #UNSUPPORTED} will be returned. 450 */ 451 public static native long getUidTcpTxSegments(int uid); 452 453 /** 454 * Get the number of TCP segments received for this UID. 455 * Does not include TCP control packets (SYN/ACKs/FIN/..). 456 * The statistics are across all interfaces. 457 * 458 * {@see android.os.Process#myUid()}. 459 * 460 * @param uid The UID of the process to examine. 461 * @return number of TCP segments. If the statistics are not supported by this device, 462 * {@link #UNSUPPORTED} will be returned. 463 */ 464 public static native long getUidTcpRxSegments(int uid); 465 466 467 /** 468 * Get the number of UDP packets sent for this UID. 469 * Includes DNS requests. 470 * The statistics are across all interfaces. 471 * 472 * {@see android.os.Process#myUid()}. 473 * 474 * @param uid The UID of the process to examine. 475 * @return number of packets. If the statistics are not supported by this device, 476 * {@link #UNSUPPORTED} will be returned. 477 */ 478 public static native long getUidUdpTxPackets(int uid); 479 480 /** 481 * Get the number of UDP packets received for this UID. 482 * Includes DNS responses. 483 * The statistics are across all interfaces. 484 * 485 * {@see android.os.Process#myUid()}. 486 * 487 * @param uid The UID of the process to examine. 488 * @return number of packets. If the statistics are not supported by this device, 489 * {@link #UNSUPPORTED} will be returned. 490 */ 491 public static native long getUidUdpRxPackets(int uid); 492 493 /** 494 * Return detailed {@link NetworkStats} for the current UID. Requires no 495 * special permission. 496 */ 497 private static NetworkStats getDataLayerSnapshotForUid(Context context) { 498 final INetworkStatsService statsService = INetworkStatsService.Stub.asInterface( 499 ServiceManager.getService(Context.NETWORK_STATS_SERVICE)); 500 final int uid = android.os.Process.myUid(); 501 try { 502 return statsService.getDataLayerSnapshotForUid(uid); 503 } catch (RemoteException e) { 504 throw new RuntimeException(e); 505 } 506 } 507 } 508