blob: bc7194b342a3894feef6ebc089c868e035bd2d27 [file] [log] [blame]
#!/usr/bin/env python
#
# Copyright 2017 - The Android Open Source Project
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
import itertools
from metrics.metric import Metric
class ProcessTimeMetric(Metric):
TIME_COMMAND = 'ps -p %s -o etimes,command | sed 1d'
# Number of seconds in 24 hours
MIN_TIME = 86400
# Fields for response dictionary
ADB_PROCESSES = 'adb_processes'
NUM_ADB_PROCESSES = 'num_adb_processes'
FASTBOOT_PROCESSES = 'fastboot_processes'
NUM_FASTBOOT_PROCESSES = 'num_fastboot_processes'
def gather_metric(self):
"""Returns ADB and Fastboot processes and their time elapsed
Returns:
A dictionary with adb/fastboot_processes as a list of serial nums or
NONE if number wasn't in command. num_adb/fastboot_processes as
the number of serials in list.
"""
# Get the process ids
pids = self.get_adb_fastboot_pids()
# Get elapsed time for selected pids
adb_processes, fastboot_processes = [], []
for pid in pids:
# Sample output:
# 232893 fastboot -s FA6BM0305019 -w
output = self._shell.run(self.TIME_COMMAND % pid).stdout
spl_ln = output.split()
# There is a potential race condition between getting pids, and the
# pid then dying, so we must check that there is output.
if spl_ln:
# pull out time in seconds
time = int(spl_ln[0])
else:
continue
# We only care about processes older than the min time
if time > self.MIN_TIME:
# ignore fork-server command, because it's not a problematic process
if 'fork-server' not in output:
# get serial number, which defaults to none
serial_number = None
if '-s' in spl_ln:
sn_index = spl_ln.index('-s')
# avoid indexing out of range
if sn_index + 1 < len(spl_ln):
serial_number = spl_ln[sn_index + 1]
# append to proper list
if 'fastboot' in output:
fastboot_processes.append(serial_number)
elif 'adb' in output:
adb_processes.append(serial_number)
# Create response dictionary
response = {
self.ADB_PROCESSES: adb_processes,
self.NUM_ADB_PROCESSES: len(adb_processes),
self.FASTBOOT_PROCESSES: fastboot_processes,
self.NUM_FASTBOOT_PROCESSES: len(fastboot_processes)
}
return response
def get_adb_fastboot_pids(self):
"""Finds a list of ADB and Fastboot process ids.
Returns:
A list of PID strings
"""
# Get ids of processes with 'adb' or 'fastboot' in name
adb_result = self._shell.get_command_pids('adb')
fastboot_result = self._shell.get_command_pids('fastboot')
# concatenate two generator objects, return as list
return list(itertools.chain(adb_result, fastboot_result))