def suspend_resume(self, suspend_time=10): """Suspends the DUT for a given time in second. @param suspend_time: Suspend time in second. """ sys_power.do_suspend(suspend_time) return True
def run_once(self): errors = 0 cpu_arch = power_utils.get_x86_cpu_arch() if not cpu_arch: cpu_arch = utils.get_cpu_arch() if cpu_arch == "arm": logging.info('OK: skipping x86-only test on %s.', cpu_arch) return raise error.TestNAError('Unknown CPU with arch "%s".' % (cpu_arch)) if cpu_arch == 'Stoney': self._cpu_type = 'Stoney' elif cpu_arch == 'Atom': self._cpu_type = 'Atom' else: self._cpu_type = 'Non-Atom' self._registers = power_utils.Registers() # Check running machine. errors += self._check_all() # Pause briefly to make sure the RTC is ready for suspend/resume. time.sleep(3) # Suspend the system to RAM and return after 10 seconds. sys_power.do_suspend(10) # Check resumed machine. errors += self._check_all() if errors > 0: raise error.TestFail('x86 register mismatch detected')
def _test_wol_magic_packet(self): """Check the Wake-on-LAN (WOL) magic packet capabilities of a device. Raises: error.TestError if WOL functionality fails """ # Magic number WOL supported capname = 'Supports Wake-on' if self._caps[capname][0].find('g') != -1: logging.info("%s support magic number WOL", self._ethname) else: raise error.TestError('%s should support magic number WOL' % self._ethname) # Check that WOL works if self._caps['Wake-on'][0] != 'g': utils.system_output("ethtool -s %s wol g" % self._ethname) self._restore_wol = True # Set RTC as backup to WOL before_secs = rtc.get_seconds() alarm_secs = before_secs + self._suspend_secs + self._threshold_secs rtc.set_wake_alarm(alarm_secs) sys_power.do_suspend(self._suspend_secs) after_secs = rtc.get_seconds() # flush RTC as it may not work subsequently if wake was not RTC rtc.set_wake_alarm(0) suspended_secs = after_secs - before_secs if suspended_secs >= (self._suspend_secs + self._threshold_secs): raise error.TestError("Device woke due to RTC not WOL")
def run_once(self): """Run a series of tests supplied by the control file. Handles iterations by adding tags with the iteration#. Normally runs each test once after each suspend. If enable_baseline is True then run an initial pass through the tests before any suspend. The test runs a series """ if self.iteration is not None and self.iteration > 1: test_tag = '%03d' % self.iteration else: test_tag = '' if self._enable_baseline: for t in self._tests: self.job.run_test(t, tag=test_tag + 'preSuspend', disable_sysinfo=True) time.sleep(random.randint(0, 3)) sys_power.do_suspend(max(self._min_suspend_s, MIN_ALLOWED_SUSPEND_S)) for t in self._tests: self.job.run_test(t, tag=test_tag + 'postSuspend', disable_sysinfo=True)
def suspend_bg_for_dark_resume(self, suspend_for_secs): """ Suspends the system for dark resume. @param suspend_for_secs : If not 0, sets a rtc alarm to wake the system after|suspend_for_secs| secs. """ if suspend_for_secs == 0: sys_power.suspend_bg_for_dark_resume() else: sys_power.do_suspend(suspend_for_secs)
def run_once(self, doctest=False): """ Run the test. :param doctest: If true we will just run our doctests. We'll set these globals to help our tests: - _testobj: An instance of this object. - _info_io: A StringIO that's stuffed into logging.info so we can see what was written there. ... """ if doctest: import doctest, inspect, StringIO global _testobj, _info_io # Keep a backup of _get_regid_to_val() since tests will clobber. old_get_regid_to_val = self._get_regid_to_val # Mock out logging.info to help tests. _info_io = StringIO.StringIO() old_logging_info = logging.info logging.info = lambda fmt, *args: _info_io.write(fmt % args) # Stash an object in a global to help tests _testobj = self try: failure_count, test_count = doctest.testmod( inspect.getmodule(self), optionflags=doctest.ELLIPSIS) finally: logging.info = old_logging_info # Technically don't need to clean this up, but let's be nice. self._get_regid_to_val = old_get_regid_to_val logging.info("Doctest ran %d tests, had %d failures", test_count, failure_count) return if utils.get_cpu_soc_family() != 'arm': raise error.TestNAError('Applicable to ARM processors only') cpuinfo = self._parse_cpu_info(utils.read_file('/proc/cpuinfo')) for cpu_id in sorted(cpuinfo.keys()): self._check_one_cpu(cpuinfo[cpu_id]) sys_power.do_suspend(self.SECS_TO_SUSPEND) for cpu_id in sorted(cpuinfo.keys()): self._check_one_cpu(cpuinfo[cpu_id])
def do_suspend(seconds): """Suspend DUT using the power manager. @param seconds: The number of seconds to suspend the device. """ return sys_power.do_suspend(seconds)
def cycling_suspend(self, cr, tabs, switches_per_suspend, total_suspend_duration, suspend_seconds, additional_sleep): """Page cycling and suspending. @return: total suspending count. """ start_time = time.time() suspend_count = 0 tab_index = 0 spurious_wakeup_count = 0 MAX_SPURIOUS_WAKEUP = 5 while time.time() - start_time < total_suspend_duration: # Page cycling for _ in range(switches_per_suspend): try: tabs[tab_index].Activate() tabs[tab_index].WaitForFrameToBeDisplayed() except Exception as e: logging.info('cannot activate tab: %s', e) tab_index = (tab_index + 1) % len(tabs) self.check_tab_discard(cr, tabs) # Suspending for the specified seconds. try: sys_power.do_suspend(suspend_seconds) except sys_power.SpuriousWakeupError: spurious_wakeup_count += 1 if spurious_wakeup_count > MAX_SPURIOUS_WAKEUP: raise error.TestFail('Too many SpuriousWakeupError.') suspend_count += 1 # Waiting for system stable, otherwise the subsequent tab # operations may fail. time.sleep(additional_sleep) self.check_tab_discard(cr, tabs) return suspend_count
def _autoconnect_cellular(self): """Verify that the DUT is able to autoconnect to cellular network.""" logging.debug('_autoconnect_cellular') service = self._find_cellular_service() logging.debug('Cellular service: %s', service) if service['ConnectionState'] == 'NotConnected': self._connect_to_cellular_network(service) self._set_autoconnect(service) logging.debug('Suspend and resume device') sys_power.do_suspend(20) service = self._find_cellular_service() utils.poll_for_condition( lambda: self._is_cellular_network_connected(service), exception=error.TestFail('Network not connected after suspend ' 'and resume.'), sleep_interval=1, timeout=60) logging.debug('Autoconnect works after suspend/resume.')
def suspend_with_youtube(self, tab, video_url): """ Suspends kernel while video is running in browser. @param tab: Object to the browser tab @param video_url: Object to video url """ tab.WaitForDocumentReadyStateToBeInteractiveOrBetter() logging.info('video url is %s', video_url) tab.EvaluateJavaScript('play("%s")' % video_url) tab.WaitForJavaScriptCondition('typeof player != "undefined"', timeout=10) self.check_video_is_playing(tab) time.sleep(2) try: sys_power.do_suspend(10) except Exception as e: logging.error(e) raise error.TestFail('====Kernel suspend failed====') time.sleep(2) self.check_video_is_playing(tab)
def run_once(self, test_hours=None, sample_hours=None, percent_initial_charge_min=0.2, max_milliwatts_standby=None): if test_hours <= sample_hours: raise error.TestFail( "Test hours must be greater than sample hours") # If we're measuring <= 6min of S3 then the S0 time is not negligible. # Note, reasonable rule of thumb is S0 idle is ~10-20 times S3 power. if sample_hours < self._min_sample_hours: raise error.TestFail("Must suspend more than %.2f hours" % \ sample_hours) # Query initial power status power_stats = power_status.get_status() power_stats.assert_battery_state(percent_initial_charge_min) charge_start = power_stats.battery[0].charge_now voltage_start = power_stats.battery[0].voltage_now max_hours = charge_start * voltage_start / \ (max_milliwatts_standby / 1000) if max_hours < test_hours: raise error.TestFail('Battery not charged adequately for test') elapsed_hours = 0 while elapsed_hours < test_hours: charge_before = power_stats.battery[0].charge_now before_suspend_secs = rtc.get_seconds() sys_power.do_suspend(sample_hours * 3600) after_suspend_secs = rtc.get_seconds() power_stats.refresh() if power_stats.percent_current_charge() < self._percent_min_charge: logging.warning( "Battery percent = %.2f%%. Too low to continue") break # check that the RTC slept the correct amount of time as there could # potentially be another wake source that would spoil the test. actual_hours = (after_suspend_secs - before_suspend_secs) / 3600.0 logging.debug("actual_hours = %.4f", actual_hours) percent_diff = math.fabs((actual_hours - sample_hours) / ((actual_hours + sample_hours) / 2) * 100) if percent_diff > 2: err_str = "Requested S3 time and actual varied by %.2f%%." \ % percent_diff raise error.TestFail(err_str) # Check resulting charge consumption charge_used = charge_before - power_stats.battery[0].charge_now logging.debug("charge_used = %.6f", charge_used) elapsed_hours += actual_hours logging.debug("elapsed_hours = %.4f", elapsed_hours) charge_end = power_stats.battery[0].charge_now voltage_end = power_stats.battery[0].voltage_now standby_hours = power_stats.battery[0].charge_full_design / \ (charge_start - charge_end) * elapsed_hours energy_used = charge_start * voltage_start - charge_end * voltage_end if energy_used <= 0: raise error.TestError("Energy used reading is suspect.") standby_milliwatts = energy_used / elapsed_hours * 1000 results = {} results['milliwatts_standby_power'] = standby_milliwatts results['hours_standby_time'] = standby_hours self.write_perf_keyval(results) # need to sleep for some time to allow network connection to return time.sleep(10)
def _suspend_to_ram(self, min_secs_suspend=2, max_secs_suspend=7): secs_to_suspend = (random.randint(min_secs_suspend, max_secs_suspend)) logging.info('Scheduling wakeup in %d seconds.\n', secs_to_suspend) sys_power.do_suspend(secs_to_suspend)
def run_once(self, mount_cycles=10, filter_dict={'bus': 'usb'}): """ @param mount_cycles: how many times to mount/unount Default: 10. @param filter_dict: storage dictionary filter. Default: match any device connected on the USB bus. """ # wait_for_device() returns (device_dictionary, # time_spent_looking_for_it), and only the dictionary is relevant for # this test storage = self.wait_for_device(filter_dict, cycles=1, mount_volume=True)[0] if not os.path.ismount(storage['mountpoint']): raise error.TestFail('filesystem %s mount failed' % filter_dict) storage_filter = {'fs_uuid': storage['fs_uuid']} # We cannot use autotemp.tempfile since we should close the descriptors # everytime the storage device is un-mounted. self._tmpfile = os.path.join(storage['mountpoint'], 'tempfile_usb_mount.tmp') while mount_cycles: mount_cycles -= 1 # Create a 1MiB random file and checksum it. storage_mod.create_file(self._tmpfile, 1 * 1024 * 1024) chksum = storage_mod.checksum_file(self._tmpfile) logging.debug('storage to umount %s', storage) # Umount the volume. self.scanner.umount_volume(storage_dict=storage) storage = self.wait_for_device(storage_filter, mount_volume=False)[0] if os.path.ismount(storage['mountpoint']): raise error.TestFail('filesystem %s unmount failed ' % storage_filter) # Mount the volume back. self.scanner.mount_volume(storage_dict=storage) storage = self.wait_for_device(storage_filter, mount_volume=False)[0] if not os.path.ismount(storage['mountpoint']): raise error.TestFail('filesystem %s mount failed' % storage_filter) # Check that the created file exists and has the same content. if not os.path.isfile(self._tmpfile): raise error.TestFail('%s: file not present after remounting' % self._tmpfile) if chksum != storage_mod.checksum_file(self._tmpfile): raise error.TestFail('%s: file content changed after ' 'remounting' % self._tmpfile) # Mount it, suspend and verify that after suspend-to-ram the # device is still mounted self.scanner.mount_volume(storage_dict=storage) storage = self.wait_for_device(storage_filter, mount_volume=False)[0] if not os.path.ismount(storage['mountpoint']): raise error.TestFail('filesystem %s mount failed ' % storage) sys_power.do_suspend(self.SECS_TO_SUSPEND) # mount_volume=False because we don't want the method to mount if # unmonted: we need to check its actual status right after suspend storage = self.wait_for_device(storage_filter, mount_volume=False)[0] if not os.path.ismount(storage['mountpoint']): raise error.TestFail('filesystem %s not mounted after suspend' % storage_filter) if not os.path.isfile(self._tmpfile): raise error.TestFail('%s: file not present anymore after ' 'remounting' % self._tmpfile) if chksum != storage_mod.checksum_file(self._tmpfile): raise error.TestFail('%s: file content changed after remounting' % self._tmpfile)
def suspend_to_ram(secs_to_suspend=5): logging.info('Scheduling wakeup in %d seconds\n', secs_to_suspend) sys_power.do_suspend(secs_to_suspend) logging.info('Woke up at %d', rtc.get_seconds())