Richard Barnette | 9a26ad6 | 2016-06-10 12:03:08 -0700 | [diff] [blame] | 1 | # Copyright 2016 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 | |
Mengqi Guo | 51d5bea | 2020-02-03 18:34:45 -0800 | [diff] [blame^] | 5 | import functools |
Richard Barnette | 9a26ad6 | 2016-06-10 12:03:08 -0700 | [diff] [blame] | 6 | import logging |
Richard Barnette | 9a26ad6 | 2016-06-10 12:03:08 -0700 | [diff] [blame] | 7 | |
| 8 | import common |
| 9 | from autotest_lib.client.common_lib import hosts |
Mengqi Guo | 51d5bea | 2020-02-03 18:34:45 -0800 | [diff] [blame^] | 10 | from autotest_lib.server.cros.servo import servo |
Richard Barnette | d72eeeb | 2018-09-05 10:08:33 -0700 | [diff] [blame] | 11 | from autotest_lib.server.hosts import repair_utils |
Richard Barnette | 9a26ad6 | 2016-06-10 12:03:08 -0700 | [diff] [blame] | 12 | |
| 13 | |
Mengqi Guo | 51d5bea | 2020-02-03 18:34:45 -0800 | [diff] [blame^] | 14 | def ignore_exception_for_non_cros_host(func): |
| 15 | """ |
| 16 | Decorator to ignore ControlUnavailableError if servo host is not cros host. |
| 17 | When using test_that command on a workstation, this enables usage of |
| 18 | additional servo devices such as servo micro and Sweetberry. This shall not |
| 19 | change any lab behavior. |
| 20 | """ |
| 21 | @functools.wraps(func) |
| 22 | def wrapper(self, host): |
| 23 | """ |
| 24 | Wrapper around func. |
| 25 | """ |
| 26 | try: |
| 27 | func(self, host) |
| 28 | except servo.ControlUnavailableError as e: |
| 29 | if host.is_cros_host(): |
| 30 | raise |
| 31 | logging.warning("Servo host is not cros host, ignore %s: %s", |
| 32 | type(e).__name__, e) |
| 33 | return wrapper |
| 34 | |
| 35 | |
Richard Barnette | 9a26ad6 | 2016-06-10 12:03:08 -0700 | [diff] [blame] | 36 | class _UpdateVerifier(hosts.Verifier): |
| 37 | """ |
| 38 | Verifier to trigger a servo host update, if necessary. |
| 39 | |
| 40 | The operation doesn't wait for the update to complete and is |
| 41 | considered a success whether or not the servo is currently |
| 42 | up-to-date. |
| 43 | """ |
| 44 | |
| 45 | def verify(self, host): |
Simran Basi | 10ad79b | 2017-01-31 12:05:24 -0800 | [diff] [blame] | 46 | # First, only run this verifier if the host is in the physical lab. |
| 47 | # Secondly, skip if the test is being run by test_that, because subnet |
| 48 | # restrictions can cause the update to fail. |
Garry Wang | 3388ffd | 2019-12-03 12:58:41 +0000 | [diff] [blame] | 49 | try: |
| 50 | if host.is_in_lab() and host.job and host.job.in_lab: |
| 51 | host.update_image(wait_for_update=False) |
| 52 | # We don't want failure from update block DUT repair action. |
| 53 | # See crbug.com/1029950. |
| 54 | except Exception as e: |
| 55 | logging.error('Failed to update servohost image: %s', e) |
Richard Barnette | 9a26ad6 | 2016-06-10 12:03:08 -0700 | [diff] [blame] | 56 | |
| 57 | @property |
| 58 | def description(self): |
| 59 | return 'servo host software is up-to-date' |
| 60 | |
| 61 | |
Kevin Cheng | 643ce8a | 2016-09-15 15:42:12 -0700 | [diff] [blame] | 62 | class _ConfigVerifier(hosts.Verifier): |
| 63 | """ |
| 64 | Base verifier for the servo config file verifiers. |
| 65 | """ |
| 66 | |
| 67 | CONFIG_FILE = '/var/lib/servod/config' |
| 68 | ATTR = '' |
| 69 | |
| 70 | @staticmethod |
| 71 | def _get_config_val(host, config_file, attr): |
| 72 | """ |
| 73 | Get the `attr` for `host` from `config_file`. |
| 74 | |
| 75 | @param host Host to be checked for `config_file`. |
| 76 | @param config_file Path to the config file to be tested. |
| 77 | @param attr Attribute to get from config file. |
| 78 | |
| 79 | @return The attr val as set in the config file, or `None` if |
| 80 | the file was absent. |
| 81 | """ |
| 82 | getboard = ('CONFIG=%s ; [ -f $CONFIG ] && ' |
| 83 | '. $CONFIG && echo $%s' % (config_file, attr)) |
| 84 | attr_val = host.run(getboard, ignore_status=True).stdout |
| 85 | return attr_val.strip('\n') if attr_val else None |
| 86 | |
| 87 | @staticmethod |
| 88 | def _validate_attr(host, val, expected_val, attr, config_file): |
| 89 | """ |
| 90 | Check that the attr setting is valid for the host. |
| 91 | |
| 92 | This presupposes that a valid config file was found. Raise an |
| 93 | execption if: |
| 94 | * There was no attr setting from the file (i.e. the setting |
| 95 | is an empty string), or |
| 96 | * The attr setting is valid, the attr is known, |
| 97 | and the setting doesn't match the DUT. |
| 98 | |
| 99 | @param host Host to be checked for `config_file`. |
| 100 | @param val Value to be tested. |
| 101 | @param expected_val Expected value. |
| 102 | @param attr Attribute we're validating. |
| 103 | @param config_file Path to the config file to be tested. |
| 104 | """ |
| 105 | if not val: |
| 106 | raise hosts.AutoservVerifyError( |
| 107 | 'config file %s exists, but %s ' |
| 108 | 'is not set' % (attr, config_file)) |
| 109 | if expected_val is not None and val != expected_val: |
| 110 | raise hosts.AutoservVerifyError( |
| 111 | '%s is %s; it should be %s' % (attr, val, expected_val)) |
| 112 | |
| 113 | |
Prathmesh Prabhu | add0030 | 2018-12-27 10:38:54 -0800 | [diff] [blame] | 114 | def _get_config(self, host): |
Kevin Cheng | 643ce8a | 2016-09-15 15:42:12 -0700 | [diff] [blame] | 115 | """ |
Prathmesh Prabhu | add0030 | 2018-12-27 10:38:54 -0800 | [diff] [blame] | 116 | Return the config file to check. |
Kevin Cheng | 643ce8a | 2016-09-15 15:42:12 -0700 | [diff] [blame] | 117 | |
| 118 | @param host Host object. |
| 119 | |
Prathmesh Prabhu | add0030 | 2018-12-27 10:38:54 -0800 | [diff] [blame] | 120 | @return The config file to check. |
Kevin Cheng | 643ce8a | 2016-09-15 15:42:12 -0700 | [diff] [blame] | 121 | """ |
Prathmesh Prabhu | add0030 | 2018-12-27 10:38:54 -0800 | [diff] [blame] | 122 | return '%s_%d' % (self.CONFIG_FILE, host.servo_port) |
Kevin Cheng | 643ce8a | 2016-09-15 15:42:12 -0700 | [diff] [blame] | 123 | |
| 124 | @property |
| 125 | def description(self): |
| 126 | return 'servo %s setting is correct' % self.ATTR |
| 127 | |
| 128 | |
| 129 | class _SerialConfigVerifier(_ConfigVerifier): |
| 130 | """ |
| 131 | Verifier for the servo SERIAL configuration. |
| 132 | """ |
| 133 | |
| 134 | ATTR = 'SERIAL' |
| 135 | |
| 136 | def verify(self, host): |
| 137 | """ |
| 138 | Test whether the `host` has a `SERIAL` setting configured. |
| 139 | |
| 140 | This tests the config file names used by the `servod` upstart |
| 141 | job for a valid setting of the `SERIAL` variable. The following |
| 142 | conditions raise errors: |
| 143 | * The SERIAL setting doesn't match the DUT's entry in the AFE |
| 144 | database. |
| 145 | * There is no config file. |
| 146 | """ |
| 147 | if not host.is_cros_host(): |
| 148 | return |
| 149 | # Not all servo hosts will have a servo serial so don't verify if it's |
| 150 | # not set. |
| 151 | if host.servo_serial is None: |
| 152 | return |
Prathmesh Prabhu | add0030 | 2018-12-27 10:38:54 -0800 | [diff] [blame] | 153 | config = self._get_config(host) |
| 154 | serialval = self._get_config_val(host, config, self.ATTR) |
Prathmesh Prabhu | d593d61 | 2018-12-27 10:41:49 -0800 | [diff] [blame] | 155 | if serialval is None: |
| 156 | raise hosts.AutoservVerifyError( |
| 157 | 'Servo serial is unconfigured; should be %s' |
| 158 | % host.servo_serial |
| 159 | ) |
| 160 | |
| 161 | self._validate_attr(host, serialval, host.servo_serial, self.ATTR, |
| 162 | config) |
Kevin Cheng | 643ce8a | 2016-09-15 15:42:12 -0700 | [diff] [blame] | 163 | |
| 164 | |
| 165 | |
| 166 | class _BoardConfigVerifier(_ConfigVerifier): |
Richard Barnette | 9a26ad6 | 2016-06-10 12:03:08 -0700 | [diff] [blame] | 167 | """ |
| 168 | Verifier for the servo BOARD configuration. |
| 169 | """ |
| 170 | |
Kevin Cheng | 643ce8a | 2016-09-15 15:42:12 -0700 | [diff] [blame] | 171 | ATTR = 'BOARD' |
Richard Barnette | 9a26ad6 | 2016-06-10 12:03:08 -0700 | [diff] [blame] | 172 | |
| 173 | def verify(self, host): |
| 174 | """ |
| 175 | Test whether the `host` has a `BOARD` setting configured. |
| 176 | |
| 177 | This tests the config file names used by the `servod` upstart |
| 178 | job for a valid setting of the `BOARD` variable. The following |
| 179 | conditions raise errors: |
| 180 | * A config file exists, but the content contains no setting |
| 181 | for BOARD. |
| 182 | * The BOARD setting doesn't match the DUT's entry in the AFE |
| 183 | database. |
| 184 | * There is no config file. |
| 185 | """ |
| 186 | if not host.is_cros_host(): |
| 187 | return |
Prathmesh Prabhu | add0030 | 2018-12-27 10:38:54 -0800 | [diff] [blame] | 188 | config = self._get_config(host) |
| 189 | boardval = self._get_config_val(host, config, self.ATTR) |
Prathmesh Prabhu | d593d61 | 2018-12-27 10:41:49 -0800 | [diff] [blame] | 190 | if boardval is None: |
| 191 | msg = 'Servo board is unconfigured' |
| 192 | if host.servo_board is not None: |
| 193 | msg += '; should be %s' % host.servo_board |
| 194 | raise hosts.AutoservVerifyError(msg) |
| 195 | |
| 196 | self._validate_attr(host, boardval, host.servo_board, self.ATTR, |
| 197 | config) |
Richard Barnette | 9a26ad6 | 2016-06-10 12:03:08 -0700 | [diff] [blame] | 198 | |
Richard Barnette | 9a26ad6 | 2016-06-10 12:03:08 -0700 | [diff] [blame] | 199 | |
| 200 | class _ServodJobVerifier(hosts.Verifier): |
| 201 | """ |
| 202 | Verifier to check that the `servod` upstart job is running. |
| 203 | """ |
| 204 | |
| 205 | def verify(self, host): |
| 206 | if not host.is_cros_host(): |
| 207 | return |
| 208 | status_cmd = 'status servod PORT=%d' % host.servo_port |
| 209 | job_status = host.run(status_cmd, ignore_status=True).stdout |
| 210 | if 'start/running' not in job_status: |
| 211 | raise hosts.AutoservVerifyError( |
| 212 | 'servod not running on %s port %d' % |
| 213 | (host.hostname, host.servo_port)) |
| 214 | |
| 215 | @property |
| 216 | def description(self): |
| 217 | return 'servod upstart job is running' |
| 218 | |
| 219 | |
Garry Wang | c042b7e | 2020-01-13 15:16:42 -0800 | [diff] [blame] | 220 | class _DiskSpaceVerifier(hosts.Verifier): |
Dana Goyette | 97a7618 | 2019-11-25 19:07:31 -0800 | [diff] [blame] | 221 | """ |
Garry Wang | c042b7e | 2020-01-13 15:16:42 -0800 | [diff] [blame] | 222 | Verifier to make sure there is enough disk space left on servohost. |
Dana Goyette | 97a7618 | 2019-11-25 19:07:31 -0800 | [diff] [blame] | 223 | """ |
Dana Goyette | 97a7618 | 2019-11-25 19:07:31 -0800 | [diff] [blame] | 224 | |
| 225 | def verify(self, host): |
Garry Wang | c042b7e | 2020-01-13 15:16:42 -0800 | [diff] [blame] | 226 | host.check_diskspace('/mnt/stateful_partition', 0.1) |
Dana Goyette | 97a7618 | 2019-11-25 19:07:31 -0800 | [diff] [blame] | 227 | |
| 228 | @property |
| 229 | def description(self): |
Garry Wang | c042b7e | 2020-01-13 15:16:42 -0800 | [diff] [blame] | 230 | return 'servohost has enough disk space.' |
Dana Goyette | 97a7618 | 2019-11-25 19:07:31 -0800 | [diff] [blame] | 231 | |
| 232 | |
Richard Barnette | 9a26ad6 | 2016-06-10 12:03:08 -0700 | [diff] [blame] | 233 | class _ServodConnectionVerifier(hosts.Verifier): |
| 234 | """ |
| 235 | Verifier to check that we can connect to `servod`. |
| 236 | |
| 237 | This tests the connection to the target servod service with a simple |
| 238 | method call. As a side-effect, all servo signals are initialized to |
| 239 | default values. |
| 240 | |
| 241 | N.B. Initializing servo signals is necessary because the power |
| 242 | button and lid switch verifiers both test against expected initial |
| 243 | values. |
| 244 | """ |
| 245 | |
| 246 | def verify(self, host): |
| 247 | host.connect_servo() |
| 248 | |
| 249 | @property |
| 250 | def description(self): |
| 251 | return 'servod service is taking calls' |
| 252 | |
| 253 | |
| 254 | class _PowerButtonVerifier(hosts.Verifier): |
| 255 | """ |
| 256 | Verifier to check sanity of the `pwr_button` signal. |
| 257 | |
| 258 | Tests that the `pwr_button` signal shows the power button has been |
| 259 | released. When `pwr_button` is stuck at `press`, it commonly |
| 260 | indicates that the ribbon cable is disconnected. |
| 261 | """ |
Simran Basi | 04a5c24 | 2016-09-21 17:35:49 -0700 | [diff] [blame] | 262 | # TODO (crbug.com/646593) - Remove list below once servo has been updated |
| 263 | # with a dummy pwr_button signal. |
Laurence Goodby | a12b5d7 | 2019-02-01 17:42:08 -0800 | [diff] [blame] | 264 | _BOARDS_WO_PWR_BUTTON = ['arkham', 'gale', 'mistral', 'storm', 'whirlwind'] |
Richard Barnette | 9a26ad6 | 2016-06-10 12:03:08 -0700 | [diff] [blame] | 265 | |
Mengqi Guo | 51d5bea | 2020-02-03 18:34:45 -0800 | [diff] [blame^] | 266 | @ignore_exception_for_non_cros_host |
Richard Barnette | 9a26ad6 | 2016-06-10 12:03:08 -0700 | [diff] [blame] | 267 | def verify(self, host): |
Simran Basi | 04a5c24 | 2016-09-21 17:35:49 -0700 | [diff] [blame] | 268 | if host.servo_board in self._BOARDS_WO_PWR_BUTTON: |
| 269 | return |
Richard Barnette | 9a26ad6 | 2016-06-10 12:03:08 -0700 | [diff] [blame] | 270 | button = host.get_servo().get('pwr_button') |
| 271 | if button != 'release': |
| 272 | raise hosts.AutoservVerifyError( |
| 273 | 'Check ribbon cable: \'pwr_button\' is stuck') |
| 274 | |
Mengqi Guo | 51d5bea | 2020-02-03 18:34:45 -0800 | [diff] [blame^] | 275 | |
Richard Barnette | 9a26ad6 | 2016-06-10 12:03:08 -0700 | [diff] [blame] | 276 | @property |
| 277 | def description(self): |
| 278 | return 'pwr_button control is normal' |
| 279 | |
| 280 | |
| 281 | class _LidVerifier(hosts.Verifier): |
| 282 | """ |
| 283 | Verifier to check sanity of the `lid_open` signal. |
| 284 | """ |
| 285 | |
Mengqi Guo | 51d5bea | 2020-02-03 18:34:45 -0800 | [diff] [blame^] | 286 | @ignore_exception_for_non_cros_host |
Richard Barnette | 9a26ad6 | 2016-06-10 12:03:08 -0700 | [diff] [blame] | 287 | def verify(self, host): |
| 288 | lid_open = host.get_servo().get('lid_open') |
| 289 | if lid_open != 'yes' and lid_open != 'not_applicable': |
| 290 | raise hosts.AutoservVerifyError( |
| 291 | 'Check lid switch: lid_open is %s' % lid_open) |
| 292 | |
| 293 | @property |
| 294 | def description(self): |
| 295 | return 'lid_open control is normal' |
| 296 | |
| 297 | |
| 298 | class _RestartServod(hosts.RepairAction): |
| 299 | """Restart `servod` with the proper BOARD setting.""" |
| 300 | |
| 301 | def repair(self, host): |
| 302 | if not host.is_cros_host(): |
| 303 | raise hosts.AutoservRepairError( |
| 304 | 'Can\'t restart servod: not running ' |
Garry Wang | 954f838 | 2019-01-23 13:49:29 -0800 | [diff] [blame] | 305 | 'embedded Chrome OS.', |
| 306 | 'servo_not_applicable_to_non_cros_host') |
Garry Wang | c1288cf | 2019-12-17 14:58:00 -0800 | [diff] [blame] | 307 | host.restart_servod() |
Richard Barnette | 9a26ad6 | 2016-06-10 12:03:08 -0700 | [diff] [blame] | 308 | |
| 309 | @property |
| 310 | def description(self): |
Kevin Cheng | 643ce8a | 2016-09-15 15:42:12 -0700 | [diff] [blame] | 311 | return 'Start servod with the proper config settings.' |
Richard Barnette | 9a26ad6 | 2016-06-10 12:03:08 -0700 | [diff] [blame] | 312 | |
| 313 | |
Richard Barnette | d72eeeb | 2018-09-05 10:08:33 -0700 | [diff] [blame] | 314 | class _ServoRebootRepair(repair_utils.RebootRepair): |
Richard Barnette | 9a26ad6 | 2016-06-10 12:03:08 -0700 | [diff] [blame] | 315 | """ |
| 316 | Reboot repair action that also waits for an update. |
| 317 | |
| 318 | This is the same as the standard `RebootRepair`, but for |
Garry Wang | ebc015b | 2019-06-06 17:45:06 -0700 | [diff] [blame] | 319 | a non-multi-DUTs servo host, if there's a pending update, |
| 320 | we wait for that to complete before rebooting. This should |
| 321 | ensure that the servo_v3 is up-to-date after reboot. Labstation |
| 322 | reboot and update is handled by labstation host class. |
Richard Barnette | 9a26ad6 | 2016-06-10 12:03:08 -0700 | [diff] [blame] | 323 | """ |
| 324 | |
| 325 | def repair(self, host): |
| 326 | if host.is_localhost() or not host.is_cros_host(): |
| 327 | raise hosts.AutoservRepairError( |
Garry Wang | 954f838 | 2019-01-23 13:49:29 -0800 | [diff] [blame] | 328 | 'Target servo is not a test lab servo', |
| 329 | 'servo_not_applicable_to_host_outside_lab') |
Garry Wang | ebc015b | 2019-06-06 17:45:06 -0700 | [diff] [blame] | 330 | if host.is_labstation(): |
Garry Wang | 79e9af6 | 2019-06-12 15:19:19 -0700 | [diff] [blame] | 331 | host.request_reboot() |
| 332 | logging.warning('Reboot labstation requested, it will be ' |
| 333 | 'handled by labstation administrative task.') |
Kevin Cheng | 5f2ba6c | 2016-09-28 10:20:05 -0700 | [diff] [blame] | 334 | else: |
Garry Wang | 3388ffd | 2019-12-03 12:58:41 +0000 | [diff] [blame] | 335 | try: |
| 336 | host.update_image(wait_for_update=True) |
| 337 | # We don't want failure from update block DUT repair action. |
| 338 | # See crbug.com/1029950. |
| 339 | except Exception as e: |
| 340 | logging.error('Failed to update servohost image: %s', e) |
Kevin Cheng | 5f2ba6c | 2016-09-28 10:20:05 -0700 | [diff] [blame] | 341 | super(_ServoRebootRepair, self).repair(host) |
Richard Barnette | 9a26ad6 | 2016-06-10 12:03:08 -0700 | [diff] [blame] | 342 | |
| 343 | @property |
| 344 | def description(self): |
| 345 | return 'Wait for update, then reboot servo host.' |
| 346 | |
| 347 | |
Wai-Hong Tam | bf6f23c | 2017-08-16 11:10:42 -0700 | [diff] [blame] | 348 | class _DutRebootRepair(hosts.RepairAction): |
| 349 | """ |
| 350 | Reboot DUT to recover some servo controls depending on EC console. |
| 351 | |
| 352 | Some servo controls, like lid_open, requires communicating with DUT through |
| 353 | EC UART console. Failure of this kinds of controls can be recovered by |
| 354 | rebooting the DUT. |
| 355 | """ |
| 356 | |
| 357 | def repair(self, host): |
| 358 | host.get_servo().get_power_state_controller().reset() |
| 359 | # Get the lid_open value which requires EC console. |
| 360 | lid_open = host.get_servo().get('lid_open') |
| 361 | if lid_open != 'yes' and lid_open != 'not_applicable': |
| 362 | raise hosts.AutoservVerifyError( |
| 363 | 'Still fail to contact EC console after rebooting DUT') |
| 364 | |
| 365 | @property |
| 366 | def description(self): |
| 367 | return 'Reset the DUT via servo' |
| 368 | |
| 369 | |
Garry Wang | c042b7e | 2020-01-13 15:16:42 -0800 | [diff] [blame] | 370 | class _DiskCleanupRepair(hosts.RepairAction): |
| 371 | """ |
| 372 | Remove old logs/metrics/crash_dumps on servohost to free up disk space. |
| 373 | """ |
| 374 | KEEP_LOGS_MAX_DAYS = 5 |
| 375 | |
| 376 | FILE_TO_REMOVE = ['/var/lib/metrics/uma-events', |
| 377 | '/var/spool/crash/*'] |
| 378 | |
| 379 | def repair(self, host): |
| 380 | if host.is_localhost(): |
| 381 | # we don't want to remove anything from local testing. |
| 382 | return |
| 383 | |
| 384 | # Remove old servod logs. |
| 385 | host.run('/usr/bin/find /var/log/servod_* -mtime +%d -print -delete' |
| 386 | % self.KEEP_LOGS_MAX_DAYS, ignore_status=True) |
| 387 | |
| 388 | # Remove pre-defined metrics and crash dumps. |
| 389 | for path in self.FILE_TO_REMOVE: |
| 390 | host.run('rm %s' % path, ignore_status=True) |
| 391 | |
| 392 | @property |
| 393 | def description(self): |
| 394 | return 'Clean up old logs/metrics on servohost to free up disk space.' |
| 395 | |
| 396 | |
Richard Barnette | 9a26ad6 | 2016-06-10 12:03:08 -0700 | [diff] [blame] | 397 | def create_servo_repair_strategy(): |
| 398 | """ |
| 399 | Return a `RepairStrategy` for a `ServoHost`. |
| 400 | """ |
Kevin Cheng | 643ce8a | 2016-09-15 15:42:12 -0700 | [diff] [blame] | 401 | config = ['brd_config', 'ser_config'] |
Richard Barnette | 9a26ad6 | 2016-06-10 12:03:08 -0700 | [diff] [blame] | 402 | verify_dag = [ |
Richard Barnette | d72eeeb | 2018-09-05 10:08:33 -0700 | [diff] [blame] | 403 | (repair_utils.SshVerifier, 'servo_ssh', []), |
Garry Wang | c042b7e | 2020-01-13 15:16:42 -0800 | [diff] [blame] | 404 | (_DiskSpaceVerifier, 'disk_space', ['servo_ssh']), |
Richard Barnette | 0f1ffc4 | 2017-03-23 13:51:24 -0700 | [diff] [blame] | 405 | (_UpdateVerifier, 'update', ['servo_ssh']), |
| 406 | (_BoardConfigVerifier, 'brd_config', ['servo_ssh']), |
| 407 | (_SerialConfigVerifier, 'ser_config', ['servo_ssh']), |
Garry Wang | c042b7e | 2020-01-13 15:16:42 -0800 | [diff] [blame] | 408 | (_ServodJobVerifier, 'job', config + ['disk_space']), |
Richard Barnette | 9a26ad6 | 2016-06-10 12:03:08 -0700 | [diff] [blame] | 409 | (_ServodConnectionVerifier, 'servod', ['job']), |
| 410 | (_PowerButtonVerifier, 'pwr_button', ['servod']), |
| 411 | (_LidVerifier, 'lid_open', ['servod']), |
| 412 | # TODO(jrbarnette): We want a verifier for whether there's |
| 413 | # a working USB stick plugged into the servo. However, |
| 414 | # although we always want to log USB stick problems, we don't |
| 415 | # want to fail the servo because we don't want a missing USB |
| 416 | # stick to prevent, say, power cycling the DUT. |
| 417 | # |
| 418 | # So, it may be that the right fix is to put diagnosis into |
| 419 | # ServoInstallRepair rather than add a verifier. |
| 420 | ] |
| 421 | |
Wai-Hong Tam | bf6f23c | 2017-08-16 11:10:42 -0700 | [diff] [blame] | 422 | servod_deps = ['job', 'servod', 'pwr_button'] |
Richard Barnette | 9a26ad6 | 2016-06-10 12:03:08 -0700 | [diff] [blame] | 423 | repair_actions = [ |
Garry Wang | c042b7e | 2020-01-13 15:16:42 -0800 | [diff] [blame] | 424 | (_DiskCleanupRepair, 'disk_cleanup', ['servo_ssh'], ['disk_space']), |
Richard Barnette | 0f1ffc4 | 2017-03-23 13:51:24 -0700 | [diff] [blame] | 425 | (_RestartServod, 'restart', ['servo_ssh'], config + servod_deps), |
Wai-Hong Tam | bf6f23c | 2017-08-16 11:10:42 -0700 | [diff] [blame] | 426 | (_ServoRebootRepair, 'servo_reboot', ['servo_ssh'], servod_deps), |
| 427 | (_DutRebootRepair, 'dut_reboot', ['servod'], ['lid_open']), |
Richard Barnette | 9a26ad6 | 2016-06-10 12:03:08 -0700 | [diff] [blame] | 428 | ] |
Garry Wang | 6753891 | 2018-12-06 14:45:04 -0800 | [diff] [blame] | 429 | return hosts.RepairStrategy(verify_dag, repair_actions, 'servo') |