1#!/usr/bin/env python3 2# 3# Copyright 2019, The Android Open Source Project 4# 5# Licensed under the Apache License, Version 2.0 (the "License"); 6# you may not use this file except in compliance with the License. 7# You may obtain a copy of the License at 8# 9# http://www.apache.org/licenses/LICENSE-2.0 10# 11# Unless required by applicable law or agreed to in writing, software 12# distributed under the License is distributed on an "AS IS" BASIS, 13# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 14# See the License for the specific language governing permissions and 15# limitations under the License. 16 17"""Helper util libraries for calling adb command line.""" 18 19import datetime 20import os 21import re 22import sys 23import time 24from typing import Optional 25 26sys.path.append(os.path.dirname(os.path.dirname(os.path.dirname( 27 os.path.abspath(__file__))))) 28import lib.cmd_utils as cmd_utils 29import lib.logcat_utils as logcat_utils 30 31 32def logcat_save_timestamp() -> str: 33 """Gets the current logcat timestamp. 34 35 Returns: 36 A string of timestamp. 37 """ 38 _, output = cmd_utils.run_adb_shell_command( 39 "date -u +\'%Y-%m-%d %H:%M:%S.%N\'") 40 return output 41 42def vm_drop_cache(): 43 """Free pagecache and slab object.""" 44 cmd_utils.run_adb_shell_command('echo 3 > /proc/sys/vm/drop_caches') 45 # Sleep a little bit to provide enough time for cache cleanup. 46 time.sleep(1) 47 48def root(): 49 """Roots adb and successive adb commands will run under root.""" 50 cmd_utils.run_shell_command('adb root') 51 52def disable_selinux(): 53 """Disables selinux setting.""" 54 _, output = cmd_utils.run_adb_shell_command('getenforce') 55 if output == 'Permissive': 56 return 57 58 print('Disable selinux permissions and restart framework.') 59 cmd_utils.run_adb_shell_command('setenforce 0') 60 cmd_utils.run_adb_shell_command('stop') 61 cmd_utils.run_adb_shell_command('start') 62 cmd_utils.run_shell_command('adb wait-for-device') 63 64def pkill(procname: str): 65 """Kills a process on device specified by the substring pattern in procname""" 66 _, pids = cmd_utils.run_shell_command('adb shell ps | grep "{}" | ' 67 'awk \'{{print $2;}}\''. 68 format(procname)) 69 70 for pid in pids.split('\n'): 71 pid = pid.strip() 72 if pid: 73 passed,_ = cmd_utils.run_adb_shell_command('kill {}'.format(pid)) 74 time.sleep(1) 75 76def parse_time_to_milliseconds(time: str) -> int: 77 """Parses the time string to milliseconds.""" 78 # Example: +1s56ms, +56ms 79 regex = r'\+((?P<second>\d+?)s)?(?P<millisecond>\d+?)ms' 80 result = re.search(regex, time) 81 second = 0 82 if result.group('second'): 83 second = int(result.group('second')) 84 ms = int(result.group('millisecond')) 85 return second * 1000 + ms 86 87def blocking_wait_for_logcat_displayed_time(timestamp: datetime.datetime, 88 package: str, 89 timeout: int) -> Optional[int]: 90 """Parses the displayed time in the logcat. 91 92 Returns: 93 the displayed time. 94 """ 95 pattern = re.compile('.*ActivityTaskManager: Displayed {}.*'.format(package)) 96 # 2019-07-02 22:28:34.469453349 -> 2019-07-02 22:28:34.469453 97 timestamp = datetime.datetime.strptime(timestamp[:-3], 98 '%Y-%m-%d %H:%M:%S.%f') 99 timeout_dt = timestamp + datetime.timedelta(0, timeout) 100 # 2019-07-01 14:54:21.946 27365 27392 I ActivityTaskManager: 101 # Displayed com.android.settings/.Settings: +927ms 102 result = logcat_utils.blocking_wait_for_logcat_pattern(timestamp, 103 pattern, 104 timeout_dt) 105 if not result or not '+' in result: 106 return None 107 displayed_time = result[result.rfind('+'):] 108 109 return parse_time_to_milliseconds(displayed_time) 110 111def delete_file_on_device(file_path: str) -> None: 112 """ Deletes a file on the device. """ 113 cmd_utils.run_adb_shell_command( 114 "[[ -f '{file_path}' ]] && rm -f '{file_path}' || " 115 "exit 0".format(file_path=file_path)) 116 117def set_prop(property: str, value: str) -> None: 118 """ Sets property using adb shell. """ 119 cmd_utils.run_adb_shell_command('setprop "{property}" "{value}"'.format( 120 property=property, value=value)) 121 122def pull_file(device_file_path: str, output_file_path: str) -> None: 123 """ Pulls file from device to output """ 124 cmd_utils.run_shell_command('adb pull "{device_file_path}" "{output_file_path}"'. 125 format(device_file_path=device_file_path, 126 output_file_path=output_file_path)) 127