Home | History | Annotate | Download | only in os
      1 /*
      2  * Copyright (C) 2015 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 package com.android.internal.os;
     17 
     18 import android.os.BatteryStats;
     19 import android.util.Log;
     20 
     21 public class BluetoothPowerCalculator extends PowerCalculator {
     22     private static final boolean DEBUG = BatteryStatsHelper.DEBUG;
     23     private static final String TAG = "BluetoothPowerCalculator";
     24     private final double mIdleMa;
     25     private final double mRxMa;
     26     private final double mTxMa;
     27     private double mAppTotalPowerMah = 0;
     28     private long mAppTotalTimeMs = 0;
     29 
     30     public BluetoothPowerCalculator(PowerProfile profile) {
     31         mIdleMa = profile.getAveragePower(PowerProfile.POWER_BLUETOOTH_CONTROLLER_IDLE);
     32         mRxMa = profile.getAveragePower(PowerProfile.POWER_BLUETOOTH_CONTROLLER_RX);
     33         mTxMa = profile.getAveragePower(PowerProfile.POWER_BLUETOOTH_CONTROLLER_TX);
     34     }
     35 
     36     @Override
     37     public void calculateApp(BatterySipper app, BatteryStats.Uid u, long rawRealtimeUs,
     38                              long rawUptimeUs, int statsType) {
     39 
     40         final BatteryStats.ControllerActivityCounter counter = u.getBluetoothControllerActivity();
     41         if (counter == null) {
     42             return;
     43         }
     44 
     45         final long idleTimeMs = counter.getIdleTimeCounter().getCountLocked(statsType);
     46         final long rxTimeMs = counter.getRxTimeCounter().getCountLocked(statsType);
     47         final long txTimeMs = counter.getTxTimeCounters()[0].getCountLocked(statsType);
     48         final long totalTimeMs = idleTimeMs + txTimeMs + rxTimeMs;
     49         double powerMah = counter.getPowerCounter().getCountLocked(statsType)
     50                 / (double)(1000*60*60);
     51 
     52         if (powerMah == 0) {
     53             powerMah = ((idleTimeMs * mIdleMa) + (rxTimeMs * mRxMa) + (txTimeMs * mTxMa))
     54                     / (1000*60*60);
     55         }
     56 
     57         app.bluetoothPowerMah = powerMah;
     58         app.bluetoothRunningTimeMs = totalTimeMs;
     59         app.btRxBytes = u.getNetworkActivityBytes(BatteryStats.NETWORK_BT_RX_DATA, statsType);
     60         app.btTxBytes = u.getNetworkActivityBytes(BatteryStats.NETWORK_BT_TX_DATA, statsType);
     61 
     62         mAppTotalPowerMah += powerMah;
     63         mAppTotalTimeMs += totalTimeMs;
     64     }
     65 
     66     @Override
     67     public void calculateRemaining(BatterySipper app, BatteryStats stats, long rawRealtimeUs,
     68                                    long rawUptimeUs, int statsType) {
     69         final BatteryStats.ControllerActivityCounter counter =
     70                 stats.getBluetoothControllerActivity();
     71 
     72         final long idleTimeMs = counter.getIdleTimeCounter().getCountLocked(statsType);
     73         final long txTimeMs = counter.getTxTimeCounters()[0].getCountLocked(statsType);
     74         final long rxTimeMs = counter.getRxTimeCounter().getCountLocked(statsType);
     75         final long totalTimeMs = idleTimeMs + txTimeMs + rxTimeMs;
     76         double powerMah = counter.getPowerCounter().getCountLocked(statsType)
     77                  / (double)(1000*60*60);
     78 
     79         if (powerMah == 0) {
     80             // Some devices do not report the power, so calculate it.
     81             powerMah = ((idleTimeMs * mIdleMa) + (rxTimeMs * mRxMa) + (txTimeMs * mTxMa))
     82                     / (1000*60*60);
     83         }
     84 
     85         // Subtract what the apps used, but clamp to 0.
     86         powerMah = Math.max(0, powerMah - mAppTotalPowerMah);
     87 
     88         if (DEBUG && powerMah != 0) {
     89             Log.d(TAG, "Bluetooth active: time=" + (totalTimeMs)
     90                     + " power=" + BatteryStatsHelper.makemAh(powerMah));
     91         }
     92 
     93         app.bluetoothPowerMah = powerMah;
     94         app.bluetoothRunningTimeMs = Math.max(0, totalTimeMs - mAppTotalTimeMs);
     95     }
     96 
     97     @Override
     98     public void reset() {
     99         mAppTotalPowerMah = 0;
    100         mAppTotalTimeMs = 0;
    101     }
    102 }
    103