• Home
  • History
  • Annotate
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 package com.android.internal.os;
2 
3 import android.os.StrictMode;
4 import android.text.TextUtils;
5 import android.util.LongSparseLongArray;
6 import android.util.Slog;
7 
8 import com.android.internal.annotations.VisibleForTesting;
9 
10 import java.io.BufferedReader;
11 import java.io.FileNotFoundException;
12 import java.io.FileReader;
13 import java.io.IOException;
14 
15 /**
16  * Reads DDR time spent at various frequencies and stores the data.  Supports diff comparison with
17  * other KernelMemoryBandwidthStats objects. The sysfs file has the format:
18  *
19  * freq time_in_bucket ... time_in_bucket
20  *      ...
21  * freq time_in_bucket ... time_in_bucket
22  *
23  * where time is measured in nanoseconds.
24  */
25 public class KernelMemoryBandwidthStats {
26     private static final String TAG = "KernelMemoryBandwidthStats";
27 
28     private static final String mSysfsFile = "/sys/kernel/memory_state_time/show_stat";
29     private static final boolean DEBUG = false;
30 
31     protected final LongSparseLongArray mBandwidthEntries = new LongSparseLongArray();
32     private boolean mStatsDoNotExist = false;
33 
updateStats()34     public void updateStats() {
35         if (mStatsDoNotExist) {
36             // Skip reading.
37             return;
38         }
39 
40         StrictMode.ThreadPolicy policy = StrictMode.allowThreadDiskReads();
41         try (BufferedReader reader = new BufferedReader(new FileReader(mSysfsFile))) {
42             parseStats(reader);
43         } catch (FileNotFoundException e) {
44             Slog.w(TAG, "No kernel memory bandwidth stats available");
45             mBandwidthEntries.clear();
46             mStatsDoNotExist = true;
47         } catch (IOException e) {
48             Slog.e(TAG, "Failed to read memory bandwidth: " + e.getMessage());
49             mBandwidthEntries.clear();
50         } finally {
51             StrictMode.setThreadPolicy(policy);
52         }
53     }
54 
55     @VisibleForTesting
parseStats(BufferedReader reader)56     public void parseStats(BufferedReader reader) throws IOException {
57         String line;
58         TextUtils.SimpleStringSplitter splitter = new TextUtils.SimpleStringSplitter(' ');
59         mBandwidthEntries.clear();
60         while ((line = reader.readLine()) != null) {
61             splitter.setString(line);
62             splitter.next();
63             int bandwidth = 0;
64             int index;
65             do {
66                 if ((index = mBandwidthEntries.indexOfKey(bandwidth)) >= 0) {
67                     mBandwidthEntries.put(bandwidth, mBandwidthEntries.valueAt(index)
68                             + Long.parseLong(splitter.next()) / 1000000);
69                 } else {
70                     mBandwidthEntries.put(bandwidth, Long.parseLong(splitter.next()) / 1000000);
71                 }
72                 if (DEBUG) {
73                     Slog.d(TAG, String.format("bandwidth: %s time: %s", bandwidth,
74                             mBandwidthEntries.get(bandwidth)));
75                 }
76                 bandwidth++;
77             } while(splitter.hasNext());
78         }
79     }
80 
getBandwidthEntries()81     public LongSparseLongArray getBandwidthEntries() {
82         return mBandwidthEntries;
83     }
84 }
85