| OLD | NEW |
| 1 /* | 1 /* |
| 2 * Copyright 2015 The WebRTC Project Authors. All rights reserved. | 2 * Copyright 2015 The WebRTC Project Authors. All rights reserved. |
| 3 * | 3 * |
| 4 * Use of this source code is governed by a BSD-style license | 4 * Use of this source code is governed by a BSD-style license |
| 5 * that can be found in the LICENSE file in the root of the source | 5 * that can be found in the LICENSE file in the root of the source |
| 6 * tree. An additional intellectual property rights grant can be found | 6 * tree. An additional intellectual property rights grant can be found |
| 7 * in the file PATENTS. All contributing project authors may | 7 * in the file PATENTS. All contributing project authors may |
| 8 * be found in the AUTHORS file in the root of the source tree. | 8 * be found in the AUTHORS file in the root of the source tree. |
| 9 */ | 9 */ |
| 10 | 10 |
| (...skipping 210 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 221 Log.d(TAG, statString); | 221 Log.d(TAG, statString); |
| 222 } | 222 } |
| 223 } | 223 } |
| 224 | 224 |
| 225 private void init() { | 225 private void init() { |
| 226 try { | 226 try { |
| 227 FileReader fin = new FileReader("/sys/devices/system/cpu/present"); | 227 FileReader fin = new FileReader("/sys/devices/system/cpu/present"); |
| 228 try { | 228 try { |
| 229 BufferedReader reader = new BufferedReader(fin); | 229 BufferedReader reader = new BufferedReader(fin); |
| 230 Scanner scanner = new Scanner(reader).useDelimiter("[-\n]"); | 230 Scanner scanner = new Scanner(reader).useDelimiter("[-\n]"); |
| 231 scanner.nextInt(); // Skip leading number 0. | 231 scanner.nextInt(); // Skip leading number 0. |
| 232 cpusPresent = 1 + scanner.nextInt(); | 232 cpusPresent = 1 + scanner.nextInt(); |
| 233 scanner.close(); | 233 scanner.close(); |
| 234 } catch (Exception e) { | 234 } catch (Exception e) { |
| 235 Log.e(TAG, "Cannot do CPU stats due to /sys/devices/system/cpu/present p
arsing problem"); | 235 Log.e(TAG, "Cannot do CPU stats due to /sys/devices/system/cpu/present p
arsing problem"); |
| 236 } finally { | 236 } finally { |
| 237 fin.close(); | 237 fin.close(); |
| 238 } | 238 } |
| 239 } catch (FileNotFoundException e) { | 239 } catch (FileNotFoundException e) { |
| 240 Log.e(TAG, "Cannot do CPU stats since /sys/devices/system/cpu/present is m
issing"); | 240 Log.e(TAG, "Cannot do CPU stats since /sys/devices/system/cpu/present is m
issing"); |
| 241 } catch (IOException e) { | 241 } catch (IOException e) { |
| 242 Log.e(TAG, "Error closing file"); | 242 Log.e(TAG, "Error closing file"); |
| 243 } | 243 } |
| 244 | 244 |
| 245 cpuFreqMax = new long[cpusPresent]; | 245 cpuFreqMax = new long[cpusPresent]; |
| 246 maxPath = new String[cpusPresent]; | 246 maxPath = new String[cpusPresent]; |
| 247 curPath = new String[cpusPresent]; | 247 curPath = new String[cpusPresent]; |
| 248 curFreqScales = new double[cpusPresent]; | 248 curFreqScales = new double[cpusPresent]; |
| 249 for (int i = 0; i < cpusPresent; i++) { | 249 for (int i = 0; i < cpusPresent; i++) { |
| 250 cpuFreqMax[i] = 0; // Frequency "not yet determined". | 250 cpuFreqMax[i] = 0; // Frequency "not yet determined". |
| 251 curFreqScales[i] = 0; | 251 curFreqScales[i] = 0; |
| 252 maxPath[i] = "/sys/devices/system/cpu/cpu" + i + "/cpufreq/cpuinfo_max_fre
q"; | 252 maxPath[i] = "/sys/devices/system/cpu/cpu" + i + "/cpufreq/cpuinfo_max_fre
q"; |
| 253 curPath[i] = "/sys/devices/system/cpu/cpu" + i + "/cpufreq/scaling_cur_fre
q"; | 253 curPath[i] = "/sys/devices/system/cpu/cpu" + i + "/cpufreq/scaling_cur_fre
q"; |
| 254 } | 254 } |
| 255 | 255 |
| 256 lastProcStat = new ProcStat(0, 0, 0); | 256 lastProcStat = new ProcStat(0, 0, 0); |
| 257 resetStat(); | 257 resetStat(); |
| 258 | 258 |
| 259 initialized = true; | 259 initialized = true; |
| 260 } | 260 } |
| 261 | 261 |
| 262 private synchronized void resetStat() { | 262 private synchronized void resetStat() { |
| 263 userCpuUsage.reset(); | 263 userCpuUsage.reset(); |
| 264 systemCpuUsage.reset(); | 264 systemCpuUsage.reset(); |
| 265 totalCpuUsage.reset(); | 265 totalCpuUsage.reset(); |
| 266 frequencyScale.reset(); | 266 frequencyScale.reset(); |
| 267 lastStatLogTimeMs = SystemClock.elapsedRealtime(); | 267 lastStatLogTimeMs = SystemClock.elapsedRealtime(); |
| 268 } | 268 } |
| 269 | 269 |
| 270 private int getBatteryLevel() { | 270 private int getBatteryLevel() { |
| 271 // Use sticky broadcast with null receiver to read battery level once only. | 271 // Use sticky broadcast with null receiver to read battery level once only. |
| 272 Intent intent = appContext.registerReceiver( | 272 Intent intent = appContext.registerReceiver( |
| 273 null /* receiver */, new IntentFilter(Intent.ACTION_BATTERY_CHANGED)); | 273 null /* receiver */, new IntentFilter(Intent.ACTION_BATTERY_CHANGED)); |
| 274 | 274 |
| 275 int batteryLevel = 0; | 275 int batteryLevel = 0; |
| 276 int batteryScale = intent.getIntExtra(BatteryManager.EXTRA_SCALE, 100); | 276 int batteryScale = intent.getIntExtra(BatteryManager.EXTRA_SCALE, 100); |
| 277 if (batteryScale > 0) { | 277 if (batteryScale > 0) { |
| 278 batteryLevel = (int) ( | 278 batteryLevel = |
| 279 100f * intent.getIntExtra(BatteryManager.EXTRA_LEVEL, 0) / batteryScal
e); | 279 (int) (100f * intent.getIntExtra(BatteryManager.EXTRA_LEVEL, 0) / batt
eryScale); |
| 280 } | 280 } |
| 281 return batteryLevel; | 281 return batteryLevel; |
| 282 } | 282 } |
| 283 | 283 |
| 284 /** | 284 /** |
| 285 * Re-measure CPU use. Call this method at an interval of around 1/s. | 285 * Re-measure CPU use. Call this method at an interval of around 1/s. |
| 286 * This method returns true on success. The fields | 286 * This method returns true on success. The fields |
| 287 * cpuCurrent, cpuAvg3, and cpuAvgAll are updated on success, and represents: | 287 * cpuCurrent, cpuAvg3, and cpuAvgAll are updated on success, and represents: |
| 288 * cpuCurrent: The CPU use since the last sampleCpuUtilization call. | 288 * cpuCurrent: The CPU use since the last sampleCpuUtilization call. |
| 289 * cpuAvg3: The average CPU over the last 3 calls. | 289 * cpuAvg3: The average CPU over the last 3 calls. |
| (...skipping 20 matching lines...) Expand all Loading... |
| 310 */ | 310 */ |
| 311 | 311 |
| 312 curFreqScales[i] = 0; | 312 curFreqScales[i] = 0; |
| 313 if (cpuFreqMax[i] == 0) { | 313 if (cpuFreqMax[i] == 0) { |
| 314 // We have never found this CPU's max frequency. Attempt to read it. | 314 // We have never found this CPU's max frequency. Attempt to read it. |
| 315 long cpufreqMax = readFreqFromFile(maxPath[i]); | 315 long cpufreqMax = readFreqFromFile(maxPath[i]); |
| 316 if (cpufreqMax > 0) { | 316 if (cpufreqMax > 0) { |
| 317 Log.d(TAG, "Core " + i + ". Max frequency: " + cpufreqMax); | 317 Log.d(TAG, "Core " + i + ". Max frequency: " + cpufreqMax); |
| 318 lastSeenMaxFreq = cpufreqMax; | 318 lastSeenMaxFreq = cpufreqMax; |
| 319 cpuFreqMax[i] = cpufreqMax; | 319 cpuFreqMax[i] = cpufreqMax; |
| 320 maxPath[i] = null; // Kill path to free its memory. | 320 maxPath[i] = null; // Kill path to free its memory. |
| 321 } | 321 } |
| 322 } else { | 322 } else { |
| 323 lastSeenMaxFreq = cpuFreqMax[i]; // A valid, previously read value. | 323 lastSeenMaxFreq = cpuFreqMax[i]; // A valid, previously read value. |
| 324 } | 324 } |
| 325 | 325 |
| 326 long cpuFreqCur = readFreqFromFile(curPath[i]); | 326 long cpuFreqCur = readFreqFromFile(curPath[i]); |
| 327 if (cpuFreqCur == 0 && lastSeenMaxFreq == 0) { | 327 if (cpuFreqCur == 0 && lastSeenMaxFreq == 0) { |
| 328 // No current frequency information for this CPU core - ignore it. | 328 // No current frequency information for this CPU core - ignore it. |
| 329 continue; | 329 continue; |
| 330 } | 330 } |
| 331 if (cpuFreqCur > 0) { | 331 if (cpuFreqCur > 0) { |
| 332 actualCpusPresent++; | 332 actualCpusPresent++; |
| 333 } | 333 } |
| (...skipping 61 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 395 return true; | 395 return true; |
| 396 } | 396 } |
| 397 | 397 |
| 398 private int doubleToPercent(double d) { | 398 private int doubleToPercent(double d) { |
| 399 return (int) (d * 100 + 0.5); | 399 return (int) (d * 100 + 0.5); |
| 400 } | 400 } |
| 401 | 401 |
| 402 private synchronized String getStatString() { | 402 private synchronized String getStatString() { |
| 403 StringBuilder stat = new StringBuilder(); | 403 StringBuilder stat = new StringBuilder(); |
| 404 stat.append("CPU User: ") | 404 stat.append("CPU User: ") |
| 405 .append(doubleToPercent(userCpuUsage.getCurrent())).append("/") | 405 .append(doubleToPercent(userCpuUsage.getCurrent())) |
| 406 .append("/") |
| 406 .append(doubleToPercent(userCpuUsage.getAverage())) | 407 .append(doubleToPercent(userCpuUsage.getAverage())) |
| 407 .append(". System: ") | 408 .append(". System: ") |
| 408 .append(doubleToPercent(systemCpuUsage.getCurrent())).append("/") | 409 .append(doubleToPercent(systemCpuUsage.getCurrent())) |
| 410 .append("/") |
| 409 .append(doubleToPercent(systemCpuUsage.getAverage())) | 411 .append(doubleToPercent(systemCpuUsage.getAverage())) |
| 410 .append(". Freq: ") | 412 .append(". Freq: ") |
| 411 .append(doubleToPercent(frequencyScale.getCurrent())).append("/") | 413 .append(doubleToPercent(frequencyScale.getCurrent())) |
| 414 .append("/") |
| 412 .append(doubleToPercent(frequencyScale.getAverage())) | 415 .append(doubleToPercent(frequencyScale.getAverage())) |
| 413 .append(". Total usage: ") | 416 .append(". Total usage: ") |
| 414 .append(doubleToPercent(totalCpuUsage.getCurrent())).append("/") | 417 .append(doubleToPercent(totalCpuUsage.getCurrent())) |
| 418 .append("/") |
| 415 .append(doubleToPercent(totalCpuUsage.getAverage())) | 419 .append(doubleToPercent(totalCpuUsage.getAverage())) |
| 416 .append(". Cores: ") | 420 .append(". Cores: ") |
| 417 .append(actualCpusPresent); | 421 .append(actualCpusPresent); |
| 418 stat.append("( "); | 422 stat.append("( "); |
| 419 for (int i = 0; i < cpusPresent; i++) { | 423 for (int i = 0; i < cpusPresent; i++) { |
| 420 stat.append(doubleToPercent(curFreqScales[i])).append(" "); | 424 stat.append(doubleToPercent(curFreqScales[i])).append(" "); |
| 421 } | 425 } |
| 422 stat.append("). Battery: ").append(getBatteryLevel()); | 426 stat.append("). Battery: ").append(getBatteryLevel()); |
| 423 if (cpuOveruse) { | 427 if (cpuOveruse) { |
| 424 stat.append(". Overuse."); | 428 stat.append(". Overuse."); |
| (...skipping 46 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 471 try { | 475 try { |
| 472 BufferedReader reader = new BufferedReader(new FileReader("/proc/stat")); | 476 BufferedReader reader = new BufferedReader(new FileReader("/proc/stat")); |
| 473 try { | 477 try { |
| 474 // line should contain something like this: | 478 // line should contain something like this: |
| 475 // cpu 5093818 271838 3512830 165934119 101374 447076 272086 0 0 0 | 479 // cpu 5093818 271838 3512830 165934119 101374 447076 272086 0 0 0 |
| 476 // user nice system idle iowait irq softirq | 480 // user nice system idle iowait irq softirq |
| 477 String line = reader.readLine(); | 481 String line = reader.readLine(); |
| 478 String lines[] = line.split("\\s+"); | 482 String lines[] = line.split("\\s+"); |
| 479 int length = lines.length; | 483 int length = lines.length; |
| 480 if (length >= 5) { | 484 if (length >= 5) { |
| 481 userTime = parseLong(lines[1]); // user | 485 userTime = parseLong(lines[1]); // user |
| 482 userTime += parseLong(lines[2]); // nice | 486 userTime += parseLong(lines[2]); // nice |
| 483 systemTime = parseLong(lines[3]); // system | 487 systemTime = parseLong(lines[3]); // system |
| 484 idleTime = parseLong(lines[4]); // idle | 488 idleTime = parseLong(lines[4]); // idle |
| 485 } | 489 } |
| 486 if (length >= 8) { | 490 if (length >= 8) { |
| 487 userTime += parseLong(lines[5]); // iowait | 491 userTime += parseLong(lines[5]); // iowait |
| 488 systemTime += parseLong(lines[6]); // irq | 492 systemTime += parseLong(lines[6]); // irq |
| 489 systemTime += parseLong(lines[7]); // softirq | 493 systemTime += parseLong(lines[7]); // softirq |
| 490 } | 494 } |
| 491 } catch (Exception e) { | 495 } catch (Exception e) { |
| 492 Log.e(TAG, "Problems parsing /proc/stat", e); | 496 Log.e(TAG, "Problems parsing /proc/stat", e); |
| 493 return null; | 497 return null; |
| 494 } finally { | 498 } finally { |
| 495 reader.close(); | 499 reader.close(); |
| 496 } | 500 } |
| 497 } catch (FileNotFoundException e) { | 501 } catch (FileNotFoundException e) { |
| 498 Log.e(TAG, "Cannot open /proc/stat for reading", e); | 502 Log.e(TAG, "Cannot open /proc/stat for reading", e); |
| 499 return null; | 503 return null; |
| 500 } catch (IOException e) { | 504 } catch (IOException e) { |
| 501 Log.e(TAG, "Problems reading /proc/stat", e); | 505 Log.e(TAG, "Problems reading /proc/stat", e); |
| 502 return null; | 506 return null; |
| 503 } | 507 } |
| 504 return new ProcStat(userTime, systemTime, idleTime); | 508 return new ProcStat(userTime, systemTime, idleTime); |
| 505 } | 509 } |
| 506 } | 510 } |
| OLD | NEW |