# Copyright (c) 2013 The Chromium OS Authors. All rights reserved.
# Use of this source code is governed by a BSD-style license that can be
# found in the LICENSE file.

import time

from autotest_lib.server.cros.servo import chrome_ec


def _inherit_docstring(cls):
    """Decorator to propagate a docstring to a subclass's method.

    @param cls Class with the method whose docstring is to be
               inherited.  The class must contain a method with
               the same name as the name of the function to be
               decorated.

    """
    def _copy_docstring(methfunc):
        """Actually copy the parent docstring to the child.

        @param methfunc Function that will inherit the docstring.

        """
        methfunc.__doc__ = getattr(cls, methfunc.__name__).__doc__
        return methfunc
    return _copy_docstring


# Constants acceptable to be passed for the `rec_mode` parameter
# to power_on().
#
# REC_ON:  Boot the DUT in recovery mode, i.e. boot from USB or
#   SD card.
# REC_OFF:  Boot in normal mode, i.e. boot from internal storage.

REC_ON = 'on'
REC_OFF = 'off'


class _PowerStateController(object):

    """Class to provide board-specific power operations.

    This class is responsible for "power on" and "power off"
    operations that can operate without making assumptions in
    advance about board state.  It offers an interface that
    abstracts out the different sequences required for different
    board types.

    """

    # Delay in seconds needed between asserting and de-asserting cold
    # or warm reset.  Subclasses will normally override this constant
    # with a board-specific value.
    _RESET_HOLD_TIME = 0.5

    # _EC_RESET_DELAY:  Time required before the EC will be working
    #   after cold reset.  Five seconds is at least twice as long as
    #   necessary for Alex, and is presumably good enough for all other
    #   systems.
    _EC_RESET_DELAY = 5.0

    def __init__(self, servo):
        """Initialize the power state control.

        @param servo Servo object providing the underlying `set` and `get`
                     methods for the target controls.

        """
        self._servo = servo

    def cold_reset(self):
        """Apply cold reset to the DUT.

        This asserts, then de-asserts the 'cold_reset' signal.
        The exact affect on the hardware varies depending on
        the board type.

        """
        self._servo.set_get_all(['cold_reset:on',
                                 'sleep:%.4f' % self._RESET_HOLD_TIME,
                                 'cold_reset:off'])
        # After the reset, give the EC the time it needs to
        # re-initialize.
        time.sleep(self._EC_RESET_DELAY)

    def warm_reset(self):
        """Apply warm reset to the DUT.

        This asserts, then de-asserts the 'warm_reset' signal.
        Generally, this causes the board to restart.

        """
        self._servo.set_get_all(['warm_reset:on',
                                 'sleep:%.4f' % self._RESET_HOLD_TIME,
                                 'warm_reset:off'])

    def recovery_supported(self):
        """Return whether the power on/off methods are supported.

        @return True means the power_on() and power_off() methods will
                not raise a NotImplementedError.  False means they will.

        """
        return False

    def power_off(self):
        """Force the DUT to power off.

        The DUT is guaranteed to be off at the end of this call,
        regardless of its previous state, provided that there is
        working EC and boot firmware.  There is no requirement for
        working OS software.

        """
        raise NotImplementedError()

    def power_on(self, rec_mode=REC_OFF):
        """Force the DUT to power on.

        Prior to calling this function, the DUT must be powered off,
        e.g. with a call to `power_off()`.

        At power on, recovery mode is set as specified by the
        corresponding argument.  When booting with recovery mode on, it
        is the caller's responsibility to unplug/plug in a bootable
        external storage device.

        If the DUT requires a delay after powering on but before
        processing inputs such as USB stick insertion, the delay is
        handled by this method; the caller is not responsible for such
        delays.

        @param rec_mode Setting of recovery mode to be applied at
                        power on. default: REC_OFF aka 'off'

        """
        raise NotImplementedError()

class _PantherController(_PowerStateController):

    """Power-state controller for Pantherand compatible boards.

    For Panther, the 'cold_reset' signal is not connected
    """

    # TODO(@moch): rename and modify appropriately
    _TIME_TO_SWITCH_OFF = 10.0
    _TIME_TO_BOOT = 10.0
    _TIME_TO_HOLD_POWER_BUTTON = 1.2

    @_inherit_docstring(_PowerStateController)
    def cold_reset(self):
        self._servo.set('pwr_button', 'press')
        time.sleep(self._TIME_TO_HOLD_POWER_BUTTON)
        self._servo.set('pwr_button', 'release')
        time.sleep(self._TIME_TO_SWITCH_OFF)

        self._servo.set('pwr_button', 'press')
        time.sleep(self._TIME_TO_HOLD_POWER_BUTTON)
        self._servo.set('pwr_button', 'release')
        time.sleep(self._TIME_TO_BOOT)


class _AlexController(_PowerStateController):

    """Power-state controller for Alex and compatible boards.

    For Alex, Lumpy, et al., the 'cold_reset' signal forces the unit
    off, and leaves it off.  Recovery mode and developer mode are
    controlled by signals from the Servo board.

    """

    # Time in seconds to allow the firmware to initialize itself and
    # present the "INSERT" screen in recovery mode before actually
    # inserting a USB stick to boot from.
    _RECOVERY_INSERT_DELAY = 10.0

    @_inherit_docstring(_PowerStateController)
    def recovery_supported(self):
        return True

    @_inherit_docstring(_PowerStateController)
    def power_off(self):
        self.cold_reset()

    @_inherit_docstring(_PowerStateController)
    def power_on(self, rec_mode=REC_OFF):
        self._servo.set_nocheck('rec_mode', rec_mode)
        self._servo.power_short_press()
        if rec_mode == REC_ON:
            time.sleep(self._RECOVERY_INSERT_DELAY)
            self._servo.set('rec_mode', REC_OFF)


class _LumpyController(_AlexController):

    """Power-state controller for Lumpy."""

    @_inherit_docstring(_AlexController)
    def power_off(self):
        # The debug header for MP Lumpy's are missing a resistor to support
        # cold_reset. Therefore to do a power off we simply long hold the
        # power button. This should cover the most common types of failures
        # in the lab. However if the unit is already off this will cause it to
        # power on instead. In this case, re-run repair a second time to
        # recover the device.
        self._servo.power_long_press()


class _StumpyController(_AlexController):

    """Power-state controller for Stumpy."""

    @_inherit_docstring(_AlexController)
    def power_off(self):
        # In test images in the lab, the 'autoreboot' upstart job will
        # commonly configure the unit so that it reboots after cold
        # reset.  Since we mustn't rely on the OS, we can't know for
        # sure whether the unit will be on or off after cold reset.
        #
        # Fortunately, the autoreboot setting only applies through one
        # reset.  So, after one reset, the unit may be on or off, but
        # autoreboot is disabled.  We can be sure to be off after a
        # second reset as long as it happens before the unit has a
        # chance to run the autoreboot job.
        self.cold_reset()
        self.cold_reset()


class _ParrotController(_PowerStateController):

    """Power-state controller for Parrot.

    On Parrot, uncontrolled assertion of `cold_reset` sometimes
    leaves the DUT unresponsive.  The `cold_reset()` method
    implemented in this class is the only known, reliable way to
    assert the `cold_reset` signal on Parrot.

    The `rec_mode` signal on Parrot is finicky.  These are the
    rules:
     1. You can't read or write the signal unless the DUT is on.
     2. The setting of the signal is only sampled during a cold
        reset.  The sampled setting applies to every boot until the
        next cold reset.
     3. After cold reset, the signal is turned off.
    N.B.  Rule 3 is subtle.  Although `rec_mode` is off after reset,
    because of rule 2, the DUT will continue to boot with the prior
    recovery mode setting until the next cold reset.

    """

    _RESET_HOLD_TIME = 0.0
    _EC_RESET_DELAY = 0.5

    # _PWR_BUTTON_READY_TIME: This represents the time after cold
    #   reset until the EC will be able to see a power button press.
    #   Used in power_off().
    _PWR_BUTTON_READY_TIME = 4

    # _REC_MODE_READY_TIME: This represents the time after power on
    #   until the EC will be able to see changes to rec_mode.  Used
    #   in power_on().
    _REC_MODE_READY_TIME = 0.75

    @_inherit_docstring(_PowerStateController)
    def recovery_supported(self):
        return True

    @_inherit_docstring(_PowerStateController)
    def cold_reset(self):
        # The sequence here leaves the DUT powered on, similar to
        # Chrome EC devices.
        self._servo.set_nocheck('pwr_button', 'press')
        super(_ParrotController, self).cold_reset()
        self._servo.set_nocheck('pwr_button', 'release')

    @_inherit_docstring(_PowerStateController)
    def power_off(self):
        self.cold_reset()
        time.sleep(self._PWR_BUTTON_READY_TIME)
        self._servo.power_short_press()

    @_inherit_docstring(_PowerStateController)
    def power_on(self, rec_mode=REC_OFF):
        self._servo.power_short_press()
        time.sleep(self._REC_MODE_READY_TIME)
        self._servo.set_nocheck('rec_mode', rec_mode)
        self.cold_reset()


class _ChromeECController(_PowerStateController):

    """Power-state controller for systems with a Chrome EC.

    For these systems, after releasing 'cold_reset' the DUT is left
    powered on.  Recovery mode is triggered by simulating keyboard
    recovery by issuing commands to the EC.

    """

    _RESET_HOLD_TIME = 0.1
    _EC_RESET_DELAY = 0.0

    _EC_CONSOLE_DELAY = 1.2

    @_inherit_docstring(_PowerStateController)
    def __init__(self, servo):
        super(_ChromeECController, self).__init__(servo)
        self._ec = chrome_ec.ChromeEC(servo)

    @_inherit_docstring(_PowerStateController)
    def recovery_supported(self):
        return True

    @_inherit_docstring(_PowerStateController)
    def power_off(self):
        self.cold_reset()
        time.sleep(self._EC_CONSOLE_DELAY)
        self._servo.power_long_press()

    @_inherit_docstring(_PowerStateController)
    def power_on(self, rec_mode=REC_OFF):
        if rec_mode == REC_ON:
            # Reset the EC to force it back into RO code; this clears
            # the EC_IN_RW signal, so the system CPU will trust the
            # upcoming recovery mode request.
            self.cold_reset()
            # Restart the EC, but leave the system CPU off...
            self._ec.reboot('ap-off')
            time.sleep(self._EC_CONSOLE_DELAY)
            # ... and tell the EC to tell the CPU we're in recovery mode.
            self._ec.set_hostevent(chrome_ec.HOSTEVENT_KEYBOARD_RECOVERY)
        self._servo.power_short_press()


class _DaisyController(_ChromeECController):
    """Power-state controller for Snow/Daisy systems."""
    _EC_CONSOLE_DELAY = 0.4


class _LinkController(_ChromeECController):

    """Power-state controller for Link.

    Link has a Chrome EC, but the hardware supports the rec_mode
    signal.

    """

    # Time in seconds to allow the BIOS and EC to detect the
    # 'rec_mode' signal after cold reset.
    _RECOVERY_DETECTION_DELAY = 2.5

    @_inherit_docstring(_ChromeECController)
    def power_off(self):
        self._ec.send_command('x86shutdown')

    @_inherit_docstring(_ChromeECController)
    def power_on(self, rec_mode=REC_OFF):
        if rec_mode == REC_ON:
            self._servo.set('rec_mode', REC_ON)
            self.cold_reset()
            time.sleep(self._RECOVERY_DETECTION_DELAY)
            self._servo.set('rec_mode', REC_OFF)
        else:
            self._servo.power_short_press()


_CONTROLLER_BOARD_MAP = {
    'daisy': _DaisyController,
    'spring': _DaisyController,
    'link': _LinkController,
    'lumpy': _LumpyController,
    'parrot': _ParrotController,
    'stumpy': _StumpyController,
    'x86-alex': _AlexController,
    'panther':_PantherController
}


def create_controller(servo, board):
    """Create a power state controller instance.

    The controller class will be selected based on the provided
    board type, and instantiated with the provided servo instance.

    @param servo Servo object that will be used to manipulate DUT
                 power states.
    @param board Board name of the DUT to be controlled.

    @returns An instance of a power state controller appropriate to
             the given board type, or `None` if the board is
             unsupported.

    """
    return _CONTROLLER_BOARD_MAP.get(board, _PowerStateController)(servo)
