Android power consumption (1) — Android power analysis method and optimization


1. Bottom current optimization

The bottom current is debugged in the mobile phone flight mode. The bottom current data of each platform may be different. For details, please refer to the current consumption data document or release note from the release. In general, the upper limit of bottom current reference data is:

The bottom current is debugged in the mobile phone flight mode. The bottom current data of each platform may be different. For details, please refer to the current consumption data document or release note from the release. In general, the upper limit of bottom current reference data is:

512M RAM < 1.5mA; 1G RAM < 2mA; 2G RAM < 2.6mA

1.1 calibration RF

Ensure that PA, antenna switch, tuner, apt and GPIO of RF work in normal state

1.2 flight mode

Turn on flight mode, turn off GPS, turn off automatic rotation screen, turn off automatic brightness adjustment, and turn off other special effects settings

The general influence of Bluetooth, WiFi, NFC, network and FM can be basically avoided by turning on flight mode;

When GPS is turned off, the influence of GPS on the bottom current can be basically ruled out;

The influence of sensor can be basically eliminated by turning off the auto rotating screen;

The influence of distance sensing can be basically eliminated by turning off the automatic brightness adjustment;

Turn off other special effects settings, such as fingerprint recognition, black screen gesture, agent sense, gesture space operation……

1.3 using perf_ defconfig

Modify device / qcom// 。 If kernel_ DEFCONFIG := _ Defconfig, change it to kernel_ DEFCONFIG := -perf_ defconfig

At the same time, the kernel code uses / kernel / arch / arm / configs / – perf_ defconfig

Is the platform name or project name

1.4 remove debugging apks




1.5 delete the application as much as possible

In setting the application, disable the running application

1.6 remove high CPU consuming processes

adb shell


When the CPU consumption is greater than 0 in sleep mode, the CPU consumption is checked. Kill the process. If the process is not killed, RM will drop the related application. For high CPU consuming kwork, we need to find out the driving reason.

1.7 manually remove all removable peripherals

Connect the mobile phone to Agilent power supply, turn on the phone, and then put the phone into standby mode. Manually remove TP, LCM, front camera, rear camera, sensor, SD card, SIM card and other peripheral devices that can be manually removed, and observe and record the change of bottom current.

# mount -o rw,remount -t vfat /dev/block/bootdevice/by-name/modem 

# cd /firmware/image 

# rm wcnss.* 

# reboot



#rmmod WLAN

Remove other chips that can be removed (sensor, NFC…)

1.8 remove drive module

In kernel / arch / arm / configs / – perf_ Remove the driver modules of sensor, TP, LCM and camera in defconfig;

Or in the makefile of the corresponding driver, remove the driver code

Then compile bootimage and burn it into the mobile phone to observe the change of bottom current

1.9 configure unused GPIO

Set the unused GPIO as input and pull down; set the GPIO configured as SPI and I2C as suspended if not used

stayboot_images/core/systemdrivers/tlmm/config/platform/TLMMChipset.xml, modify the GPIO configuration. The initial state of GPIO is configured here, and the driver may modify GPIO.

Comparing the schematic diagram of the project with the schematic diagram of the platform, the extra NC GPIO in the schematic diagram of the project should be disposed of.

1.10 check power related NV items

Need to confirm with CE. It is generally as follows:

1027 = 0

1895 = 0

1892 = 0

1962 = 0

4679 = 16

4201 = 0

3851 = 0

3852 = 6

7157 = 1

69745 rxd_enable = 0


NV3581 = 0

NV3852 = 6

1.11 check GPIO, LDO and bus

Compare the schematic diagram of the project with the reference schematic diagram of the platform, and check the configuration of GPIO, LDO and bus with different hardware.

To measure the voltage of GPIO, LDO and I2C during dormancy, a multimeter is needed to accurately measure.

The voltage of each I2C GPIO is measured accurately with a multimeter.

If possible, measure the accurate voltage of all LDOS before and after sleep.

For LDO, the debugging method is as follows:

(1) ADB shell closes LDO

If L3 is off:

cd /sys/kernel/debug/regulator/8916_l3/

echo 0 > enable

(2) LDO is used by too many devices, so it is not suitable to use the ADB shell to close it. You can debug as follows:

cat /sys/kernel/debug/regulator/8916_l6/consumers
[email protected]_32:/sys/kernel/debug/regulator/8916_l6 $ cat consumers 

Device-Supply EN Min_uV Max_uV load_uA 

0-000c-vio Y 1800000 1800000 0 

0-0068-vi2c N 1800000 1800000 0 

5-0038-vcc_i2c Y 1800000 1800000 0 

1a98000.qcom,mdss_dsi-vddio N 1800000 1800000 100 

1a98300.qcom,mdss_dsi_pll-vddio N 1800000 1800000 100 

8916_l6 N 0 0 0

This allows you to see which devices requested ldo6. Then find the corresponding code, turn off LDO when sleeping and turn it on when waking up.

0-000c: hanging on i2c0, the address is 0xc

Check whether the driver code of the two devices has executed the regulator_ enable。

(3) Close LDO by register address

If the address of ldo6 is 0x14546, the shutdown method is as follows:

# cd /sys/kernel/debug/spmi/spmi-0

(4) Turn off MPP

Close MPP1, MPP2, mpp3 and mpp4 before sleep

For example, the register addresses of pm8916 are respectively 0xa046, 0xa146, 0xa246 and 0xa346

Cat data to see the original value before closing.

The method of reading GPIO status is as follows:

(1)GPIO dump

In order to get the GPIO status during sleep, add the following print:

#include "tlmm_hwio.h" 

void deep_sleep_enter(void) 


uint64 sleep_duration; 



SWEVENT(SLEEP_DEEP_SLEEP_ENTER_COMPLETE, sleep_mode.deep_sleep_mode, sleep_duration); 

// For test 


int num; 

int i=11; 

volatile uint32 cfg ,inout, val; 


num = 122; //8916 only. Need modify for 8974/8x10/8x26 etc. 


cfg = *(volatile uint32*)HWIO_TLMM_GPIO_CFGn_ADDR(i); //(0x61000000 + i * 0x1000) 

inout = *(volatile uint32*)HWIO_TLMM_GPIO_IN_OUTn_ADDR(i);//(0x61000004 + i * 0x1000) 

val = ((cfg << 16)&0xffff0000) | (inout&0xffff); 



mpm_sw_done(sleep_mode.deep_sleep_mode, sleep_duration); 

} while(FALSE); 


Add the following code for test.

Then modify:


if 'USES_QDSS_SWE' in env: 


events = [['SLEEP_DEEP_SLEEP_ENTER=320','deep sleep enter. (sleep mode: %d) (count: %d)'], 

['SLEEP_DEEP_SLEEP_EXIT','deep sleep exit (sleep mode: %d)'], 

['SLEEP_NO_DEEP_SLEEP','bail early from deep sleep. (sleep mode: %d) (reason: %d)'], 

['SLEEP_RPM_HALT_ENTER','rpm halt enter'], 

['SLEEP_RPM_HALT_EXIT','rpm halt exit'], 

['SLEEP_MPM_INTS','pending mpm interrupts at wakeup: (interrupt_status_1 %d), (interrupt_status_2 %d)'], 

['SLEEP_DEEP_SLEEP_ENTER_COMPLETE','deep sleep exit complete (sleep mode: %d)'], 

['SLEEP_DEEP_SLEEP_EXIT_COMPLETE','deep sleep exit (sleep mode: %d)'], 

['SLEEP_MPM_WAKEUP_TIME','mpm wake up time (wakeup time: 0x%0.8x%0.8x)'], 

['SLEEP_GPIO_DUMP','gpio [%d] configuration is %d'],

['SLEEP_EVENT_LAST=383','sleep last event placeholder']

Add sleep_ GPIO_ Dump.

Compiling and writing rpm.mbn 。

Let the machine sleep, enter download, grab dump, and then send the following log to the platform for technical support analysis.




And the newly compiled rpm_ AAAAANAZR.elf 。

In RPM, it may not be very convenient. You can also use busybox to read registers, such as reading gpio11:

Physical Address for GPIO_CFG11 = 0x100B000 

[email protected]:/data/busybox # ./busybox devmem 0x100B000 32 

./busybox devmem 0x100B000 32 





GPIO_OE = "1" Output Enable

1.12 rpm dump

Grasp RPM dump, and then provide log to platform technical support.

The method is as follows:

(1)ps_ Hold ground

In the dormant state, connect PS_ If the hold to the ground is less than 200ms, the machine will enter the emergency download state. Plug in the USB, qpst will automatically get the memory dump, and then upload the following files:




And rpm_ AAAAANAZR.elf (ELF that must match the compilation time of the machine)

(2) Change reset to download key

Send these commands and change reset to download key:

# cd /sys/kernel/debug/spmi/spmi-0 

# echo 0x844 > address 

# echo 4 > count 

# cat data 

00840 -- -- -- -- 0F 07 04 00 

# echo 0x00 0x00 0x01 0x00 > data 

# cat data 

00840 -- -- -- -- 00 00 01 00 

# echo 0x00 0x00 0x01 0x80 > data 

# cat data 

00840 -- -- -- -- 00 00 01 80

Then long press the key to enter download. After that, the method of grabbing log is the same as above.

If you can’t download, you need to confirm:


In addition, it may be related to NV 4399 and 905.

1.13 check rpm_ stats

Check rpm_ Whether stats enter VDD min or XO / no shutdown. Use the following command to check the RPM lower power mode count:

cat /sys/kernel/debug/rpm_stats

If the count of Vmin is 0, it indicates that the device has never entered VDD min; if non zero means that the device has entered VDD min_ min。

RPM Mode: xosd


time in last mode(msec):0

time since last mode(sec):794

actual last sleep(msec):0

RPM Mode:vmin


time in last mode(msec):0

time since last mode(sec):359

actual last sleep(msec):110000

1.14 using trace32

Complete and detailed GPIO / Clk / PMIC information can be dump out to exclude abnormal state during sleep.

2. Standby current optimization

2.1 check through ADB log

adb logcat -v time > YearMounthDayHourMinute_logcat.txt   //main log

adb logcat -v time -b events > YearMounthDayHourMinute_logcat_event.txt   //event log

adb logcat -v time -b radio > YearMounthDayHourMinute_logcat_radio.txt    //radio log

adb shell dmesg > YearMounthDayHourMinute_dmesg.txt                 //kernel log

The power consumption problem time tracking table can be used to accurately track power consumption anomalies.

You can use the following command to open the kernel log of the specified file (for example, qpnp ADC TM. C and qpnp ADC common. C)

adb shell mount -t debugfs none /sys/kernel/debug

adb shell "echo 8 > /proc/sys/kernel/printk" 

adb shell "echo 'file qpnp-adc-tm.c +p' > /sys/kernel/debug/dynamic_debug/control"

adb shell "echo 'file qpnp-adc-common.c +p' > /sys/kernel/debug/dynamic_debug/control"

adb shell "echo 8 > /proc/sys/kernel/printk"

Open log for the specified function to qpnpint_ handle_ IRQ as an example:

adb shell "echo 'func qpnpint_handle_irq +p' > /sys/kernel/debug/dynamic_debug/control"

#logkit#Call logkit APK to save logcat, dmesg, crash, qxdm, GPU log and other log information to the mobile phone.

2.2 top

Through the top command, you can query the application with high CPU consumption. If an application has been occupying the CPU and the application is not opened at this time, the application is likely to cause a standby exception.

adb shell


“CPU utilization in this scenario” is user + system + Iow + IRQ

Module related CPU usage is the sum of the CPU usage of module related processes

2.3 running

Set the application to be running. You can see the running application or service. Do not drop the application or service and observe the change of standby current.

2.4 wakeup debug mask

Debugging wakeup can enable the debug function, and then grab the log. Some debug information will be added to the log.

mount -t debugfs none /sys/kernel/debug  

echo 1 > /sys/kernel/debug/clk/debug_suspend  

echo 1 > /sys/module/msm_show_resume_irq/parameters/debug_mask  

echo 4 > /sys/module/wakelock/parameters/debug_mask  

echo 1 > /sys/module/lpm_levels/parameters/debug_mask  

echo 0x16 > /sys/module/smd/parameters/debug_mask

2.5 wakelock


Both kernel wakelock and userspace wakelock may prevent the system from sleeping. All wakeup_ All sources are stored in the sys node / sys / kernel / debug / wakeup_ In sources.

The file contains the following information:

(1)the total amount of time a wakeup source has prevented suspend

(2)the amount of time a wakelock has been active since the last activation etc. The unit of time is milliseconds.


active_ The since value can be used to confirm whether wakelock is preventing hibernation. If the value is not zero, then the wakelock is working and preventing hibernation.

3. Get wakeup_ Commands for sources

adb root 67754400

adb remount

adb shell 

cat /sys/kernel/debug/wakeup_sources > /data/wakeup_sources.txt

adb pull /data/wakeup_sources.txt

Get wakeup_ sources.txt After that, open it through Excel_ An item whose since is not 0 is wakeup source. Take Table 2 as an example_ The active since value corresponding to dwc3 is 481756 > 0, which means that MSM_ Dwc3 driver is preventing the system from sleeping. The next step is to check the MSM_ Dwc3 driver code and related log.

Table 2 wakeup source opened in Excel

4、power:wakeup_source_activate and power:wakeup_source_deactivate events

When a wakeup source is acquired or released, power:wakeup_ source_ Activate and power:wakeup_ source_ The activate event will be written to the trace buffer to record the frequency of wakeup source being used by the driver.

How to turn this function on:

echo "power:wakeup_source_activate power:wakeup_source_deactivate" > /sys/kernel/debug/tracing/set_event

The power:wakeup_source_activate and power:wakeup_source_deactivate events are written to the trace buffer any time a wakeup source is acquired or released and it can provide information on how often a wakeup source is being used by a driver.  

To enable these events, you can enable following:  

echo "power:wakeup_source_activate power:wakeup_source_deactivate" > /sys/kernel/debug/tracing/set_event 

Once the above done, the traces will be present in /sys/kernel/debug/tracing/trace.

2.6 powertop

Powertop is used to view the CPU running statistics to help debug power problems. Powertop is used as follows:

powertop --h

Usage: powertop [OPTION...]

n -d, --dump read wakeups once and print list of top offenders

n -t, --time=DOUBLE default time to gather data in seconds

n -r, --reset Reset PM stats data

n -h, --help Show this help message

n -v, --version Show version information and exit

How to get powertop log:

  1. Connect mobile phone to computer via USB

  2. ADB shell, and then execute the following command:

sleep 10 && /data/powertop [-r] -d -t 30 > /data/powertop.log &

  1. Unplug the USB cable and wait for 10 seconds to start the power consumption test

  2. Plug in USB

  3. adb pull /data/powertop.log

2.7 CPU freq log

Open the CPU freq change log:

mount -t debugfs none /sys/kernel/debug  

cd /sys/kernel/debug 

echo -n 'file acpuclock-8x60.c +p' > dynamic_debug/control 

echo -n 'file acpuclock-krait.c +p' > dynamic_debug/control

View CPU freq Stats:

cat /sys/devices/system/cpu/cpu0/cpufreq/stats 

cat /sys/devices/system/cpu/cpu1/cpufreq/stats 

cat /sys/devices/system/cpu/cpu2/cpufreq/stats 

cat /sys/devices/system/cpu/cpu3/cpufreq/stats

To lock cpu freg:

echo the same freq to following sys mode will lock cpu freq to the setting freq. 



To enable/disable specific freq for ACPU

ACPU freq table is defined in acpu_freq_tbl_* structure of specific platform. 


For 8974, it is defined in arch/arm/mach-msm/acpuclock-8974.c. the first column of following table used to enable/disable freq in the row: 1:enable, 0:disable  

static struct acpu_level acpu_freq_tbl_2p3g_pvs0[] __initdata = { 

{ 1, { 300000, PLL_0, 0, 0 }, L2(0), 800000, 72 }, 

{ 0, { 345600, HFPLL, 2, 36 }, L2(1), 800000, 83 }, 

{ 1, { 422400, HFPLL, 2, 44 }, L2(2), 800000, 101 }, 

{ 0, { 499200, HFPLL, 2, 52 }, L2(2), 805000, 120 }, 

{ 0, { 576000, HFPLL, 1, 30 }, L2(3), 815000, 139 }, 

{ 1, { 652800, HFPLL, 1, 34 }, L2(3), 825000, 159 }, 

{ 1, { 729600, HFPLL, 1, 38 }, L2(4), 835000, 180 }, 

{ 0, { 806400, HFPLL, 1, 42 }, L2(4), 845000, 200 }, 

{ 1, { 883200, HFPLL, 1, 46 }, L2(4), 855000, 221 }, 

{ 1, { 960000, HFPLL, 1, 50 }, L2(9), 865000, 242 }, 

{ 1, { 1036800, HFPLL, 1, 54 }, L2(10), 875000, 264 }, 

{ 0, { 1113600, HFPLL, 1, 58 }, L2(10), 890000, 287 }, 

{ 1, { 1190400, HFPLL, 1, 62 }, L2(10), 900000, 308 }, 


{ 1, { 1958400, HFPLL, 1, 102 }, L2(19), 1040000, 565 }, 

{ 0, { 2035200, HFPLL, 1, 106 }, L2(19), 1055000, 596 }, 

{ 0, { 2112000, HFPLL, 1, 110 }, L2(19), 1070000, 627 }, 

{ 0, { 2188800, HFPLL, 1, 114 }, L2(19), 1085000, 659 }, 

{ 1, { 2265600, HFPLL, 1, 118 }, L2(19), 1100000, 691 }, 

{ 0, { 0 } } 


2.8 Hoplug cores

Core 0 can’t be hotplugged, Core 1/2/3 can be hotplugged,

To remove core :

echo 0 > /sys/devices/system/cpu/cpu1/online 

echo 0 > /sys/devices/system/cpu/cpu2/online 

echo 0 > /sys/devices/system/cpu/cpu3/online

To add back core:

echo 1 > /sys/devices/system/cpu/cpu1/online

echo 1 > /sys/devices/system/cpu/cpu2/online

echo 1 > /sys/devices/system/cpu/cpu3/online

2.9 Scaling governor

To check scaling governor:

cat /sys/devices/system/cpu/cpu0/cpufreq/scaling_governor

To set new governor:

For example:

echo ondemand > /sys/devices/system/cpu/cpu0/cpufreq/scaling_governor

2.10 Mpdecision

Use Mpdecison daemon to start/stop/enable debug with commands below:

Start mpdecison: 

start mpdecision 


Stop mpdecison:

stop mpdecision

Enable mpdecision debug :

start mpdecision --debug

2.11 Power feature enable/disable

Following sys node can be used to enable the lower resource,

echo 2 > /sys/module/lpm_resources/enable_low_power/l2 

echo 1 > /sys/module/lpm_resources/enable_low_power/pxo 

echo 1 > /sys/module/lpm_resources/enable_low_power/vdd_dig 

echo 1 > /sys/module/lpm_resources/enable_low_power/vdd_mem 

echo 1 > /sys/module/pm_8x60/modes/cpu0/power_collapse/suspend_enabled 

echo 1 > /sys/module/pm_8x60/modes/cpu1/power_collapse/suspend_enabled 

echo 1 > /sys/module/pm_8x60/modes/cpu2/power_collapse/suspend_enabled 

echo 1 > /sys/module/pm_8x60/modes/cpu3/power_collapse/suspend_enabled 

echo 1 > /sys/module/pm_8x60/modes/cpu0/power_collapse/idle_enabled 

echo 1 > /sys/module/pm_8x60/modes/cpu0/standalone_power_collapse/suspend_enabled

echo 1 > /sys/module/pm_8x60/modes/cpu1/standalone_power_collapse/suspend_enabled

echo 1 > /sys/module/pm_8x60/modes/cpu2/standalone_power_collapse/suspend_enabled 

echo 1 > /sys/module/pm_8x60/modes/cpu3/standalone_power_collapse/suspend_enabled

echo 1 > /sys/module/pm_8x60/modes/cpu0/standalone_power_collapse/idle_enabled 

echo 1 > /sys/module/pm_8x60/modes/cpu1/standalone_power_collapse/idle_enabled 

echo 1 > /sys/module/pm_8x60/modes/cpu2/standalone_power_collapse/idle_enabled 

echo 1 > /sys/module/pm_8x60/modes/cpu3/standalone_power_collapse/idle_enabled 

echo 0 to above sys node will disable related low power mode.

2.12 Check system alarm

get android alarms and statistics: 

adb dumpsys alarm > alarms.txt


enable android debug message in logcat: 

setprop persist.alarm.debug 1

2.13 Kernel timer check

Sys node /proc/timer_stats can be used to check kernel timer stastics, customer can use following command to get timer statics in specific scenario:

echo 0 > /proc/timer_stats && sleep 10 && echo 1 > /proc/timer_stats && sleep 30 && cat /proc/timer_stats > /data/timer_stats &

OEMs need to provide file /data/timer_stats to salesforce case for check.

3. Optimization of other power consumption items

3.1 effect of screen on power consumption

Different brightness levels of the screen result in different power consumption. The lower the brightness, the lower the power consumption. Lowering the default backlight brightness level of the screen and the backlight brightness level at the maximum screen brightness setting can optimize the overall power consumption performance of the mobile phone.

Backlight level LCD node:


The default backlight level and the highest brightness backlight level need to consider both user experience and power performance, and need to be evaluated together.

In addition, debugging the FPS frame rate of LCD can also optimize the power consumption.


Dynamic frequency modulation and voltage regulation of CPU / GPU can optimize the power performance of mobile phone. The impact is holistic and systematic.

CPU frequency reduction is mainly achieved in two ways, both of which can achieve the goal of frequency reduction.

1. Set the CPU to work in powersave mode. When this mode is set, the CPU will always work at the lowest frequency (300000 Hz). At this time, the most power-saving mobile phone, but there may be a mobile phone running stuck.

For example, set cpu0 to powersave mode, and the command is:

echo "powersave" > /sys/devices/system/cpu/cpu0/cpufreq/scaling_governor

For example, set CPU1 to powersave mode, and the command is:

echo "powersave" > /sys/devices/system/cpu/cpu1/cpufreq/scaling_governor

Ex780 has 4 CPUs (cpu0 ~ cpu3), which can be processed in this way

2. Limit the maximum CPU frequency to limit the upper limit of CPU operating frequency

The CPU (cpu0 ~ cpu3) can select the following frequency values, that is, these values can be used as the CPU frequency upper limit. The upper frequency limit can be set according to the actual scene needs. In the super power saving mode, the purpose of CPU work is: low CPU frequency + no card operation, both must be guaranteed.

The CPU can select the frequency:

300000 422400 652800 729600 883200 960000 1036800 1190400 1267200 1497600 1574400 1728000 1958400 2265600 2457600

For example, set the upper frequency limit of cpu0 to 960000

echo 960000 > /sys/devices/system/cpu/cpu0/cpufreq/scaling_max_freq

For example, set the upper frequency limit of cpu0 to 422400

echo 422400 > /sys/devices/system/cpu/cpu0/cpufreq/scaling_max_freq

GPU debugging is similar to CPU, and the device node path is / sys / devices / fdb00000.qcom, kgsl-3d0 / kgsl / kgsl-3d0

3.3 CPU utilization

If the occupancy rate of CPU is too high, the application will generally lead to high power consumption.

adb shell

top -m 6

3.4 game power consumption

It can be optimized from the following aspects:

Reduce the brightness level of screen backlight;

The CPU and GPU are used for dynamic frequency regulation and voltage regulation, and the lower frequency limit of CPU and GPU is lowered;

Thermal was used- engine.conf 。

3.5 high power consumption of camera

Reduce the camera frame rate;

Reduce the brightness level of screen backlight;

The CPU and GPU are used for dynamic frequency regulation and voltage regulation, and the lower frequency limit of CPU and GPU is lowered;

Thermal was used- engine.conf 。