blob: 2464f4ce5cf580a4a459fcfb52c57ca6319b21ea [file] [log] [blame]
Ryan Harrisonb74d2242013-02-04 11:36:49 -05001# Copyright (c) 2013 The Chromium OS Authors. All rights reserved.
2# Use of this source code is governed by a BSD-style license that can be
3# found in the LICENSE file.
4
Alex Miller3c4e37e2014-06-02 07:00:01 -07005"""
6Provides utility class for stopping and restarting services
7
8When using this class, one likely wishes to do the following:
9
10 def initialize(self):
11 self._services = service_stopper.ServiceStopper(['service'])
12 self._services.stop_services()
13
14
15 def cleanup(self):
16 self._services.start_services()
17
18As this ensures that the services will be off before the test code runs, and
19the test framework will ensure that the services are restarted through any
20code path out of the test.
21"""
Ryan Harrisonb74d2242013-02-04 11:36:49 -050022
23import logging
Todd Broch5cc92d52019-11-12 08:27:47 -080024import os
Ryan Harrisonb74d2242013-02-04 11:36:49 -050025
26from autotest_lib.client.bin import utils
Todd Broch821a6392019-11-11 12:41:46 -080027from autotest_lib.client.cros import upstart
Ryan Harrisonb74d2242013-02-04 11:36:49 -050028
Alex Miller3c4e37e2014-06-02 07:00:01 -070029
Ryan Harrisonb74d2242013-02-04 11:36:49 -050030class ServiceStopper(object):
31 """Class to manage CrOS services.
32 Public attributes:
33 services_to_stop: list of services that should be stopped
34
35 Public constants:
36 POWER_DRAW_SERVICES: list of services that influence power test in
37 unpredictable/undesirable manners.
38
39 Public methods:
40 stop_sevices: stop running system services.
41 restore_services: restore services that were previously stopped.
42
43 Private attributes:
44 _services_stopped: list of services that were successfully stopped
45 """
46
Todd Brochb6c937a2018-08-21 15:39:54 -070047 POWER_DRAW_SERVICES = ['powerd', 'update-engine', 'vnc']
Ryan Harrisonb74d2242013-02-04 11:36:49 -050048
Todd Broch1a4f4fd2018-05-07 11:16:14 -070049 # List of thermal throttling services that should be disabled.
50 # - temp_metrics for link.
51 # - thermal for daisy, snow, pit etc.
Todd Broch30a97962018-05-07 11:41:40 -070052 # - dptf for intel >= baytrail
Todd Broch1a4f4fd2018-05-07 11:16:14 -070053 # TODO(ihf): cpu_quiet on nyan isn't a service. We still need to disable it
54 # on nyan. See crbug.com/357457.
Todd Broch30a97962018-05-07 11:41:40 -070055 THERMAL_SERVICES = ['dptf', 'temp_metrics', 'thermal']
Todd Broch1a4f4fd2018-05-07 11:16:14 -070056
Ryan Harrisonb74d2242013-02-04 11:36:49 -050057 def __init__(self, services_to_stop=[]):
58 """Initialize instance of class.
59
60 By Default sets an empty list of services.
61 """
62 self.services_to_stop = services_to_stop
63 self._services_stopped = []
64
65
66 def stop_services(self):
67 """Turn off managed services."""
68
69 for service in self.services_to_stop:
Todd Broch821a6392019-11-11 12:41:46 -080070 if not upstart.has_service(service):
Ryan Harrisonb74d2242013-02-04 11:36:49 -050071 continue
Todd Broch821a6392019-11-11 12:41:46 -080072 if not upstart.is_running(service):
73 continue
74 upstart.stop_job(service)
75 self._services_stopped.append(service)
Ryan Harrisonb74d2242013-02-04 11:36:49 -050076
77
78 def restore_services(self):
79 """Restore services that were stopped."""
80 for service in reversed(self._services_stopped):
Todd Broch821a6392019-11-11 12:41:46 -080081 upstart.restart_job(service)
Ryan Harrisonb74d2242013-02-04 11:36:49 -050082 self._services_stopped = []
Alex Miller3c4e37e2014-06-02 07:00:01 -070083
84
85 def __enter__(self):
86 self.stop_services()
87 return self
88
89
90 def __exit__(self, exnval, exntype, exnstack):
91 self.restore_services()
Christopher Wiley0efabf22015-03-12 11:24:35 -070092
93
94 def close(self):
95 """Equivalent to restore_services."""
96 self.restore_services()
Todd Broch1a4f4fd2018-05-07 11:16:14 -070097
98
Todd Broch5cc92d52019-11-12 08:27:47 -080099 def _dptf_fixup_pl1(self):
100 """For intel devices that don't set their PL1 override in coreboot's
101 devicetree.cb (See 'register "tdp_pl1_override') stopping DPTF will
102 change the PL1 limit to the platform default. For eve (KBL-Y) that
103 would be 4.5W. To workaround this until FW can be fixed we should
104 instead query what the PL1 limit is for the proc_thermal driver and
105 write it to the PL1 constraint.
106
107 TODO(b/144020442)
108 """
109 pl1_max_path = \
110 '/sys/devices/pci0000:00/0000:00:04.0/power_limits/power_limit_0_max_uw'
111 pl1_constraint_path = \
112 '/sys/class/powercap/intel-rapl:0/constraint_0_power_limit_uw'
113 if not os.path.exists(pl1_max_path):
114 return
115
116 pl1 = int(utils.read_one_line(pl1_max_path))
117 logging.debug('PL1 set to %d uw', pl1)
118 utils.system('echo %d > %s' % (pl1, pl1_constraint_path))
119
120
Todd Broch1a4f4fd2018-05-07 11:16:14 -0700121def get_thermal_service_stopper():
122 """Convenience method to retrieve thermal service stopper."""
123 return ServiceStopper(services_to_stop=ServiceStopper.THERMAL_SERVICES)