faft: firmware_Cr50DeferredECReset releases power_button on test fail
This patch cleans up the dut control status on test failure, like
releasing power button, turning on dts mode, changing servo_v4_role
as source.
At test initialization, it checks whether the board is suitable for
this test by checking RDD recognition issue.
BUG=None
BRANCH=None
TEST=manually ran test_that on Coral, Fleex(Octopus) and Atlas.
[Coral]
----------------------------------------------------------------------
firmware_Cr50DeferredECReset [ PASSED ]
firmware_Cr50DeferredECReset/firmware_Cr50DeferredECReset [ PASSED ]
----------------------------------------------------------------------
[Fleex]
----------------------------------------------------------------------
firmware_Cr50DeferredECReset [ PASSED ]
firmware_Cr50DeferredECReset/firmware_Cr50DeferredECReset [ PASSED ]
----------------------------------------------------------------------
[Atlas]
----------------------------------------------------------------------
firmware_Cr50DeferredECReset [ PASSED ]
firmware_Cr50DeferredECReset TEST_NA:
This board has a RDD recognition issue
firmware_Cr50DeferredECReset/firmware_Cr50DeferredECReset [ PASSED ]
firmware_Cr50DeferredECReset/firmware_Cr50DeferredECReset TEST_NA:
This board has a RDD recognition issue
----------------------------------------------------------------------
Change-Id: I54514698a0c36a35a2f8b3aef1ff4515b4d3ee7e
Signed-off-by: Namyoon Woo <namyoon@chromium.org>
Reviewed-on: https://chromium-review.googlesource.com/1551959
Legacy-Commit-Queue: Commit Bot <commit-bot@chromium.org>
Reviewed-by: Mary Ruthven <mruthven@chromium.org>
diff --git a/server/site_tests/firmware_Cr50DeferredECReset/control b/server/site_tests/firmware_Cr50DeferredECReset/control
index 7d8dde8..7433722 100644
--- a/server/site_tests/firmware_Cr50DeferredECReset/control
+++ b/server/site_tests/firmware_Cr50DeferredECReset/control
@@ -7,7 +7,7 @@
AUTHOR = "Chrome OS Team"
NAME = "firmware_Cr50DeferredECReset"
PURPOSE = "Verify Deferred EC Reset."
-ATTRIBUTES = ""
+ATTRIBUTES = "suite:faft_cr50_pvt, suite:faft_cr50_prepvt, suite:faft_cr50_tot"
TIME = "SHORT"
TEST_TYPE = "server"
DEPENDENCIES = "servo"
diff --git a/server/site_tests/firmware_Cr50DeferredECReset/firmware_Cr50DeferredECReset.py b/server/site_tests/firmware_Cr50DeferredECReset/firmware_Cr50DeferredECReset.py
index 244bccd..3f52c40 100644
--- a/server/site_tests/firmware_Cr50DeferredECReset/firmware_Cr50DeferredECReset.py
+++ b/server/site_tests/firmware_Cr50DeferredECReset/firmware_Cr50DeferredECReset.py
@@ -17,14 +17,54 @@
After this, EC_RST_L should be deasserted as soon as the power button
gets released.
+
+ Attributes
+ version: test version number
+ CUTOFF_DELAY: duration in second to keep cr50 powered off,
+ PD_SETTLE_TIME: duration in second to wait PD to be stable
+ HAS_CR50_RESET_ODL: boolean if 'cr50_reset_odl' control is available
"""
version = 1
+ CUTOFF_DELAY = 10
+ PD_SETTLE_TIME = 3
+ HAS_CR50_RESET_ODL = False
+
+ def cr50_power_on_reset(self):
+ """Perform a power-on-reset on cr50.
+ If cr50_reset_odl control is available, then use it.
+ Otherwise, disconnect and reconnect battery and power source.
+ """
+ if self.HAS_CR50_RESET_ODL:
+ self.servo.set('cr50_reset_odl', 'on')
+
+ time.sleep(self.CUTOFF_DELAY)
+
+ self.servo.set('cr50_reset_odl', 'off')
+ else:
+ # Stop power delivery to dut
+ logging.info('Stop charging')
+ self.servo.set('servo_v4_role', 'snk')
+
+ # Battery Cutoff
+ logging.info('Cut battery off')
+ self.ec.send_command('cutoff')
+
+ time.sleep(self.CUTOFF_DELAY)
+
+ # Enable power delivery to dut
+ logging.info('Start charging')
+ self.servo.set('servo_v4_role', 'src')
+
+ time.sleep(self.PD_SETTLE_TIME)
def initialize(self, host, cmdline_args, full_args):
- """Initialize the test and check if
- cr50 is exists,
- DTS is controllable, and
- power delivery mode and power button is adjustable.
+ """Initialize the test and check if cr50 exists, DTS is controllable,
+ and power delivery mode and power button is adjustable.
+
+ Raises:
+ TestFail: If test initialization setup fails.
+ TestNAError: If the dut is not proper for this test for its RDD
+ recognition problem.
"""
super(firmware_Cr50DeferredECReset, self).initialize(host, cmdline_args,
full_args)
@@ -33,48 +73,88 @@
'access to the Cr50 console')
if not self.cr50.servo_v4_supports_dts_mode():
raise error.TestNAError('Need working servo v4 DTS control')
+ self.dts_restore = self.servo.get('servo_v4_dts_mode')
+ # Fast open cr50 and check if testlab is enabled.
self.fast_open(enable_testlab=True)
if not self.cr50.testlab_is_on():
- raise error.TestNAError('Cr50 testlab mode needs to be enabled')
-
- # Test the external power delivery
- self.servo.set('servo_v4_role', 'snk')
- time.sleep(3)
-
- rv = self.ec.send_command_get_output('chgstate',['.*>'])[0].strip()
- logging.info(rv)
- if not 'ac = 0' in rv:
- raise error.TestFail('Failed in setting servo_v4_role sink')
-
- # Test stopping the external power delivery
- self.servo.set('servo_v4_role', 'src')
- time.sleep(3)
-
- rv = self.ec.send_command_get_output('chgstate',['.*>'])[0].strip()
- logging.info(rv)
- if not 'ac = 1' in rv:
- raise error.TestFail('Failed in setting servo_v4_role source')
+ raise error.TestNAError('Cr50 testlab mode is not enabled')
# Test if the power button is adjustable.
self.servo.set('pwr_button', 'press')
self.servo.set('pwr_button', 'release')
+ # Check if 'cr50_reset_odl' controlis available.
+ try:
+ self.servo.get('cr50_reset_odl')
+ self.HAS_CR50_RESET_ODL = True
+ except error.TestFail:
+ self.HAS_CR50_RESET_ODL = False
+
+ # Test the external power delivery
+ self.servo.set('servo_v4_role', 'snk')
+ time.sleep(self.PD_SETTLE_TIME)
+
+ rv = self.ec.send_command_get_output('chgstate',['.*>'])[0].strip()
+ logging.info(rv)
+ if 'ac = 0' not in rv:
+ raise error.TestFail('Failed to set servo_v4_role sink')
+
+ # Test stopping the external power delivery
+ self.servo.set('servo_v4_role', 'src')
+ time.sleep(self.PD_SETTLE_TIME)
+
+ rv = self.ec.send_command_get_output('chgstate',['.*>'])[0].strip()
+ logging.info(rv)
+ if 'ac = 1' not in rv:
+ raise error.TestFail('Failed to set servo_v4_role source')
+
+ # Check if the dut has any RDD recognition issue.
+ # First, cut off power source and hold the power button.
+ # disable RDD connection.
+ self.servo.set('servo_v4_dts_mode', 'off')
+ self.servo.set('pwr_button', 'press')
+ self.cr50_power_on_reset()
+ try:
+ # Third, check if the rdd status is disconnected.
+ # If not, terminate the test.
+ ccdstate = self.cr50.get_ccdstate()
+
+ if ccdstate['Rdd'].lower() != 'disconnected':
+ raise error.TestNAError('This board has a RDD recognition'
+ ' issue')
+ finally:
+ self.servo.set_nocheck('servo_v4_dts_mode', self.dts_restore)
+ self.servo.set_nocheck('pwr_button', 'release')
+ time.sleep(self.PD_SETTLE_TIME)
+
+ self.servo.power_short_press() # Wake up AP
+
+ logging.info('Initialization is done')
+
def check_ecrst_asserted(self, expect_assert):
"""Ask CR50 whether EC_RST_L is asserted or deasserted.
Args:
expect_assert: True if it is expected asserted.
False otherwise.
+
+ Raises:
+ TestFail: if ecrst value is not as expected.
"""
# If the console is responsive, then the EC is awake.
- rv = self.cr50.send_command_get_output('ecrst',
- ['EC_RST_L is \w{0,2}asserted.*>'])[0].strip()
- logging.info(rv)
expecting_txt = ' asserted' if expect_assert else ' deasserted'
+ logging.info('Checking if ecrst is %s', expecting_txt)
- if not expecting_txt in rv:
+ try:
+ rv = self.cr50.send_command_get_output('ecrst',
+ ['(?i)EC_RST_L is \w{0,2}asserted.*>'])[0].strip()
+ logging.info(rv)
+ except error.TestError as e:
+ raise error.TestFail(str(e))
+
+ if expecting_txt.lower() not in rv.lower():
raise error.TestFail(rv)
def ping_ec(self, expect_response):
@@ -83,18 +163,22 @@
Args:
expect_response: True if EC should respond
False otherwise.
+ Raises:
+ TestFail: if ec responsiveness is not as same as expected.
"""
try:
- rv = self.ec.send_command_get_output('time',
- ['time.*>'])[0].strip()
+ logging.info('Checking if ec is %sresponsive',
+ '' if expect_response else 'not ')
+ rv = self.ec.send_command_get_output('help', ['.*>'])[0].strip()
except error.TestFail as e:
- logging.info(e)
+ logging.info(str(e))
if 'Timeout waiting for response' in str(e):
if not expect_response:
return
raise e
else:
if not expect_response:
+ logging.error('EC should not respond')
raise error.TestFail(rv)
def test_deferred_ec_reset(self, power_button_hold, rdd_enable,
@@ -110,54 +194,53 @@
reset.
False otherwise.
"""
- logging.info('Test deferred_ec_reset starts.')
+ logging.info('Test deferred_ec_reset starts')
logging.info('Power button held: %s', power_button_hold)
logging.info('RDD connection : %s', rdd_enable)
- # Stop power delivery to DUT
- self.servo.set('servo_v4_role', 'snk')
- time.sleep(3)
+ try:
+ # enable RDD Connection (or disable) before power-on-reset
+ self.servo.set('servo_v4_dts_mode', 'on' if rdd_enable else 'off')
- # Battery Cutoff
- self.ec.send_command('cutoff')
- time.sleep(3)
+ # Set power button before the dut loses power,
+ # because the power button value cannot be changed during power-off.
+ self.servo.set('pwr_button',
+ 'press' if power_button_hold else 'release')
- # EC should not respond
- self.ping_ec(False)
+ # Do a power-on-reset on CR50.
+ self.cr50_power_on_reset()
- # press (or release) the power button
- power_button_setval = 'press' if power_button_hold else 'release'
- # call set_nocheck, since power button shall be recognized as pressed
- # at this point.
- self.servo.set_nocheck('pwr_button', power_button_setval)
+ # Wait for a while
+ wait_sec = 30
+ logging.info('waiting for %d seconds', wait_sec)
+ time.sleep(wait_sec)
- # enable RDD Connection (or disable)
- self.servo.set_nocheck('servo_v4_dts_mode',
- 'on' if rdd_enable else 'off')
- time.sleep(self.cr50.SHORT_WAIT)
+ # Check if EC_RST_L is asserted and EC is on.
+ # (or EC_RST_L deasserted and EC off)
+ self.check_ecrst_asserted(not expect_ec_response)
+ self.ping_ec(expect_ec_response)
- # Enable power delivery to DUT
- self.servo.set('servo_v4_role', 'src')
+ # Release power button
+ logging.info('Power button released')
+ self.servo.set('pwr_button', 'release')
+ time.sleep(self.PD_SETTLE_TIME)
- # Wait for a while
- wait_sec = 30
- logging.info('waiting for %d seconds', wait_sec)
- time.sleep(wait_sec)
+ # Check if EC_RST_L is deasserted and EC is on.
+ self.check_ecrst_asserted(False)
+ self.ping_ec(True)
- # Check if EC_RST_L is asserted (or deasserted) and EC is on (or off).
- self.check_ecrst_asserted(not expect_ec_response)
- self.ping_ec(expect_ec_response)
+ finally:
+ if self.HAS_CR50_RESET_ODL:
+ self.servo.set_nocheck('cr50_reset_odl', 'off')
+ else:
+ self.servo.set_nocheck('servo_v4_role', 'src')
- # Release power button
- self.servo.set('pwr_button', 'release')
+ self.servo.set_nocheck('servo_v4_dts_mode', self.dts_restore)
+ time.sleep(1)
- # Check if EC_RST_L is deasserted and EC is on.
- self.check_ecrst_asserted(False)
- self.ping_ec(True)
-
- # Recover CCD
- if self.servo.get('servo_v4_dts_mode') == 'off':
- self.cr50.ccd_enable()
+ # Press power button to wake up AP, and releases it soon
+ # in any cases.
+ self.servo.power_short_press()
def run_once(self):
"""Test deferred EC reset feature. """
@@ -165,19 +248,21 @@
# Release power button and disable RDD on power-on reset.
# EC should be running.
self.test_deferred_ec_reset(power_button_hold=False, rdd_enable=False,
- expect_ec_response=True)
+ expect_ec_response=True)
# Release power button but enable RDD on power-on reset.
# EC should be running.
self.test_deferred_ec_reset(power_button_hold=False, rdd_enable=True,
- expect_ec_response=True)
+ expect_ec_response=True)
# Hold power button but disable RDD on power-on reset.
# EC should be running.
self.test_deferred_ec_reset(power_button_hold=True, rdd_enable=False,
- expect_ec_response=True)
+ expect_ec_response=True)
# Hold power button and enable RDD on power-on reset.
# EC should not be running.
self.test_deferred_ec_reset(power_button_hold=True, rdd_enable=True,
- expect_ec_response=False)
+ expect_ec_response=False)
+
+ logging.info('Test is done')