#!/usr/bin/env python

r"""
Provide useful ipmi functions.
"""

import re
import gen_print as gp
import gen_misc as gm
import gen_cmd as gc
import gen_robot_keyword as grk
import gen_robot_utils as gru
import bmc_ssh_utils as bsu
import var_funcs as vf
import ipmi_client as ic
import tempfile
gru.my_import_resource("ipmi_client.robot")
from robot.libraries.BuiltIn import BuiltIn
import json


def get_sol_info():
    r"""
    Get all SOL info and return it as a dictionary.

    Example use:

    Robot code:
    ${sol_info}=  get_sol_info
    Rpvars  sol_info

    Output:
    sol_info:
      sol_info[Info]:                                SOL parameter 'Payload Channel (7)'
                                                     not supported - defaulting to 0x0e
      sol_info[Character Send Threshold]:            1
      sol_info[Force Authentication]:                true
      sol_info[Privilege Level]:                     USER
      sol_info[Set in progress]:                     set-complete
      sol_info[Retry Interval (ms)]:                 100
      sol_info[Non-Volatile Bit Rate (kbps)]:        IPMI-Over-Serial-Setting
      sol_info[Character Accumulate Level (ms)]:     100
      sol_info[Enabled]:                             true
      sol_info[Volatile Bit Rate (kbps)]:            IPMI-Over-Serial-Setting
      sol_info[Payload Channel]:                     14 (0x0e)
      sol_info[Payload Port]:                        623
      sol_info[Force Encryption]:                    true
      sol_info[Retry Count]:                         7
    """

    status, ret_values = grk.run_key_u("Run IPMI Standard Command  sol info")

    # Create temp file path.
    temp = tempfile.NamedTemporaryFile()
    temp_file_path = temp.name

    # Write sol info to temp file path.
    text_file = open(temp_file_path, "w")
    text_file.write(ret_values)
    text_file.close()

    # Use my_parm_file to interpret data.
    sol_info = gm.my_parm_file(temp_file_path)

    return sol_info


def set_sol_setting(setting_name, setting_value):
    r"""
    Set SOL setting with given value.

    # Description of argument(s):
    # setting_name                  SOL setting which needs to be set (e.g.
    #                               "retry-count").
    # setting_value                 Value which needs to be set (e.g. "7").
    """

    status, ret_values = grk.run_key_u("Run IPMI Standard Command  sol set "
                                       + setting_name + " " + setting_value)

    return status


def execute_ipmi_cmd(cmd_string,
                     ipmi_cmd_type='inband',
                     print_output=1,
                     ignore_err=0,
                     **options):
    r"""
    Run the given command string as an IPMI command and return the stdout,
    stderr and the return code.

    Description of argument(s):
    cmd_string                      The command string to be run as an IPMI
                                    command.
    ipmi_cmd_type                   'inband' or 'external'.
    print_output                    If this is set, this function will print
                                    the stdout/stderr generated by
                                    the IPMI command.
    ignore_err                      Ignore error means that a failure
                                    encountered by running the command
                                    string will not be raised as a python
                                    exception.
    options                         These are passed directly to the
                                    create_ipmi_ext_command_string function.
                                    See that function's prolog for details.
    """

    if ipmi_cmd_type == 'inband':
        IPMI_INBAND_CMD = BuiltIn().get_variable_value("${IPMI_INBAND_CMD}")
        cmd_buf = IPMI_INBAND_CMD + " " + cmd_string
        return bsu.os_execute_command(cmd_buf,
                                      print_out=print_output,
                                      ignore_err=ignore_err)

    if ipmi_cmd_type == 'external':
        cmd_buf = ic.create_ipmi_ext_command_string(cmd_string, **options)
        rc, stdout, stderr = gc.shell_cmd(cmd_buf,
                                          print_output=print_output,
                                          ignore_err=ignore_err,
                                          return_stderr=1)
        return stdout, stderr, rc


def get_lan_print_dict(channel_number='', ipmi_cmd_type='external'):
    r"""
    Get IPMI 'lan print' output and return it as a dictionary.

    Here is an example of the IPMI lan print output:

    Set in Progress         : Set Complete
    Auth Type Support       : MD5
    Auth Type Enable        : Callback : MD5
                            : User     : MD5
                            : Operator : MD5
                            : Admin    : MD5
                            : OEM      : MD5
    IP Address Source       : Static Address
    IP Address              : x.x.x.x
    Subnet Mask             : x.x.x.x
    MAC Address             : xx:xx:xx:xx:xx:xx
    Default Gateway IP      : x.x.x.x
    802.1q VLAN ID          : Disabled
    Cipher Suite Priv Max   : Not Available
    Bad Password Threshold  : Not Available

    Given that data, this function will return the following dictionary.

    lan_print_dict:
      [Set in Progress]:                              Set Complete
      [Auth Type Support]:                            MD5
      [Auth Type Enable]:
        [Callback]:                                   MD5
        [User]:                                       MD5
        [Operator]:                                   MD5
        [Admin]:                                      MD5
        [OEM]:                                        MD5
      [IP Address Source]:                            Static Address
      [IP Address]:                                   x.x.x.x
      [Subnet Mask]:                                  x.x.x.x
      [MAC Address]:                                  xx:xx:xx:xx:xx:xx
      [Default Gateway IP]:                           x.x.x.x
      [802.1q VLAN ID]:                               Disabled
      [Cipher Suite Priv Max]:                        Not Available
      [Bad Password Threshold]:                       Not Available

    Description of argument(s):
    ipmi_cmd_type                   The type of ipmi command to use (e.g.
                                    'inband', 'external').
    """

    channel_number = str(channel_number)
    # Notice in the example of data above that 'Auth Type Enable' needs some
    # special processing.  We essentially want to isolate its data and remove
    # the 'Auth Type Enable' string so that key_value_outbuf_to_dict can
    # process it as a sub-dictionary.
    cmd_buf = "lan print " + channel_number + " | grep -E '^(Auth Type Enable)" +\
        "?[ ]+: ' | sed -re 's/^(Auth Type Enable)?[ ]+: //g'"
    stdout1, stderr, rc = execute_ipmi_cmd(cmd_buf, ipmi_cmd_type,
                                           print_output=0)

    # Now get the remainder of the data and exclude the lines with no field
    # names (i.e. the 'Auth Type Enable' sub-fields).
    cmd_buf = "lan print " + channel_number + " | grep -E -v '^[ ]+: '"
    stdout2, stderr, rc = execute_ipmi_cmd(cmd_buf, ipmi_cmd_type,
                                           print_output=0)

    # Make auth_type_enable_dict sub-dictionary...
    auth_type_enable_dict = vf.key_value_outbuf_to_dict(stdout1, to_lower=0,
                                                        underscores=0)

    # Create the lan_print_dict...
    lan_print_dict = vf.key_value_outbuf_to_dict(stdout2, to_lower=0,
                                                 underscores=0)
    # Re-assign 'Auth Type Enable' to contain the auth_type_enable_dict.
    lan_print_dict['Auth Type Enable'] = auth_type_enable_dict

    return lan_print_dict


def get_ipmi_power_reading(strip_watts=1):
    r"""
    Get IPMI power reading data and return it as a dictionary.

    The data is obtained by issuing the IPMI "power reading" command.  An
    example is shown below:

    Instantaneous power reading:                   234 Watts
    Minimum during sampling period:                234 Watts
    Maximum during sampling period:                234 Watts
    Average power reading over sample period:      234 Watts
    IPMI timestamp:                           Thu Jan  1 00:00:00 1970
    Sampling period:                          00000000 Seconds.
    Power reading state is:                   deactivated

    For the data shown above, the following dictionary will be returned.

    result:
      [instantaneous_power_reading]:              238 Watts
      [minimum_during_sampling_period]:           238 Watts
      [maximum_during_sampling_period]:           238 Watts
      [average_power_reading_over_sample_period]: 238 Watts
      [ipmi_timestamp]:                           Thu Jan  1 00:00:00 1970
      [sampling_period]:                          00000000 Seconds.
      [power_reading_state_is]:                   deactivated

    Description of argument(s):
    strip_watts                     Strip all dictionary values of the
                                    trailing " Watts" substring.
    """

    status, ret_values = \
        grk.run_key_u("Run IPMI Standard Command  dcmi power reading")
    result = vf.key_value_outbuf_to_dict(ret_values)

    if strip_watts:
        result.update((k, re.sub(' Watts$', '', v)) for k, v in result.items())

    return result


def get_mc_info():
    r"""
    Get IPMI mc info data and return it as a dictionary.

    The data is obtained by issuing the IPMI "mc info" command.  An
    example is shown below:

    Device ID                 : 0
    Device Revision           : 0
    Firmware Revision         : 2.01
    IPMI Version              : 2.0
    Manufacturer ID           : 42817
    Manufacturer Name         : Unknown (0xA741)
    Product ID                : 16975 (0x424f)
    Product Name              : Unknown (0x424F)
    Device Available          : yes
    Provides Device SDRs      : yes
    Additional Device Support :
        Sensor Device
        SEL Device
        FRU Inventory Device
        Chassis Device
    Aux Firmware Rev Info     :
        0x00
        0x00
        0x00
        0x00

    For the data shown above, the following dictionary will be returned.
    mc_info:
      [device_id]:                       0
      [device_revision]:                 0
      [firmware_revision]:               2.01
      [ipmi_version]:                    2.0
      [manufacturer_id]:                 42817
      [manufacturer_name]:               Unknown (0xA741)
      [product_id]:                      16975 (0x424f)
      [product_name]:                    Unknown (0x424F)
      [device_available]:                yes
      [provides_device_sdrs]:            yes
      [additional_device_support]:
        [additional_device_support][0]:  Sensor Device
        [additional_device_support][1]:  SEL Device
        [additional_device_support][2]:  FRU Inventory Device
        [additional_device_support][3]:  Chassis Device
      [aux_firmware_rev_info]:
        [aux_firmware_rev_info][0]:      0x00
        [aux_firmware_rev_info][1]:      0x00
        [aux_firmware_rev_info][2]:      0x00
        [aux_firmware_rev_info][3]:      0x00
    """

    status, ret_values = \
        grk.run_key_u("Run IPMI Standard Command  mc info")
    result = vf.key_value_outbuf_to_dict(ret_values, process_indent=1)

    return result


def get_sdr_info():
    r"""
    Get IPMI sdr info data and return it as a dictionary.

    The data is obtained by issuing the IPMI "sdr info" command.  An
    example is shown below:

    SDR Version                         : 0x51
    Record Count                        : 216
    Free Space                          : unspecified
    Most recent Addition                :
    Most recent Erase                   :
    SDR overflow                        : no
    SDR Repository Update Support       : unspecified
    Delete SDR supported                : no
    Partial Add SDR supported           : no
    Reserve SDR repository supported    : no
    SDR Repository Alloc info supported : no

    For the data shown above, the following dictionary will be returned.
    mc_info:

      [sdr_version]:                         0x51
      [record_Count]:                        216
      [free_space]:                          unspecified
      [most_recent_addition]:
      [most_recent_erase]:
      [sdr_overflow]:                        no
      [sdr_repository_update_support]:       unspecified
      [delete_sdr_supported]:                no
      [partial_add_sdr_supported]:           no
      [reserve_sdr_repository_supported]:    no
      [sdr_repository_alloc_info_supported]: no
    """

    status, ret_values = \
        grk.run_key_u("Run IPMI Standard Command  sdr info")
    result = vf.key_value_outbuf_to_dict(ret_values, process_indent=1)

    return result


def get_aux_version(version_id):
    r"""
    Get IPMI Aux version info data and return it.

    Description of argument(s):
    version_id                      The data is obtained by from BMC
                                    /etc/os-release
                                    (e.g. "xxx-v2.1-438-g0030304-r3-gfea8585").

    In the prior example, the 3rd field is "438" is the commit version and
    the 5th field is "r3" and value "3" is the release version.

    Aux version return from this function 4380003.
    """

    # Commit version.
    count = re.findall("-(\\d{1,4})-", version_id)

    # Release version.
    release = re.findall("-r(\\d{1,4})", version_id)
    if release:
        aux_version = count[0] + "{0:0>4}".format(release[0])
    else:
        aux_version = count[0] + "0000"

    return aux_version


def get_fru_info():
    r"""
    Get fru info and return it as a list of dictionaries.

    The data is obtained by issuing the IPMI "fru print -N 50" command.  An
    example is shown below:

    FRU Device Description : Builtin FRU Device (ID 0)
     Device not present (Unspecified error)

    FRU Device Description : cpu0 (ID 1)
     Board Mfg Date        : Sun Dec 31 18:00:00 1995
     Board Mfg             : <Manufacturer Name>
     Board Product         : PROCESSOR MODULE
     Board Serial          : YA1934315964
     Board Part Number     : 02CY209

    FRU Device Description : cpu1 (ID 2)
     Board Mfg Date        : Sun Dec 31 18:00:00 1995
     Board Mfg             : <Manufacturer Name>
     Board Product         : PROCESSOR MODULE
     Board Serial          : YA1934315965
     Board Part Number     : 02CY209

    For the data shown above, the following list of dictionaries will be
    returned.

    fru_obj:
      fru_obj[0]:
        [fru_device_description]:  Builtin FRU Device (ID 0)
        [state]:                   Device not present (Unspecified error)
      fru_obj[1]:
        [fru_device_description]:  cpu0 (ID 1)
        [board_mfg_date]:          Sun Dec 31 18:00:00 1995
        [board_mfg]:               <Manufacturer Name>
        [board_product]:           PROCESSOR MODULE
        [board_serial]:            YA1934315964
        [board_part_number]:       02CY209
      fru_obj[2]:
        [fru_device_description]:  cpu1 (ID 2)
        [board_mfg_date]:          Sun Dec 31 18:00:00 1995
        [board_mfg]:               <Manufacturer Name>
        [board_product]:           PROCESSOR MODULE
        [board_serial]:            YA1934315965
        [board_part_number]:       02CY209
    """

    status, ret_values = \
        grk.run_key_u("Run IPMI Standard Command  fru print -N 50")

    # Manipulate the "Device not present" line to create a "state" key.
    ret_values = re.sub("Device not present", "state : Device not present",
                        ret_values)

    return [vf.key_value_outbuf_to_dict(x) for x in re.split("\n\n",
                                                             ret_values)]


def get_component_fru_info(component='cpu',
                           fru_objs=None):
    r"""
    Get fru info for the given component and return it as a list of
    dictionaries.

    This function calls upon get_fru_info and then filters out the unwanted
    entries.  See get_fru_info's prolog for a layout of the data.

    Description of argument(s):
    component                       The component (e.g. "cpu", "dimm", etc.).
    fru_objs                        A fru_objs list such as the one returned
                                    by get_fru_info.  If this is None, then
                                    this function will call get_fru_info to
                                    obtain such a list.
                                    Supplying this argument may improve
                                    performance if this function is to be
                                    called multiple times.
    """

    if fru_objs is None:
        fru_objs = get_fru_info()
    return\
        [x for x in fru_objs
         if re.match(component + '([0-9]+)? ', x['fru_device_description'])]


def get_user_info(userid, channel_number=1):
    r"""
    Get user info using channel command and return it as a dictionary.

    Description of argument(s):
    userid          The userid (e.g. "1", "2", etc.).
    channel_number  The user's channel number (e.g. "1").

    Note: If userid is blank, this function will return a list of dictionaries.  Each list entry represents
    one userid record.

    The data is obtained by issuing the IPMI "channel getaccess" command.  An
    example is shown below for user id 1 and channel number 1.

    Maximum User IDs     : 15
    Enabled User IDs     : 1
    User ID              : 1
    User Name            : root
    Fixed Name           : No
    Access Available     : callback
    Link Authentication  : enabled
    IPMI Messaging       : enabled
    Privilege Level      : ADMINISTRATOR
    Enable Status        : enabled

    For the data shown above, the following dictionary will be returned.

    user_info:
      [maximum_userids]:     15
      [enabled_userids:      1
      [userid]               1
      [user_name]            root
      [fixed_name]           No
      [access_available]     callback
      [link_authentication]  enabled
      [ipmi_messaging]       enabled
      [privilege_level]      ADMINISTRATOR
      [enable_status]        enabled
    """

    status, ret_values = grk.run_key_u("Run IPMI Standard Command  channel getaccess "
                                       + str(channel_number) + " " + str(userid))

    if userid == "":
        return vf.key_value_outbuf_to_dicts(ret_values, process_indent=1)
    else:
        return vf.key_value_outbuf_to_dict(ret_values, process_indent=1)


def channel_getciphers_ipmi():

    r"""
    Run 'channel getciphers ipmi' command and return the result as a list of dictionaries.

    Example robot code:
    ${ipmi_channel_ciphers}=  Channel Getciphers IPMI
    Rprint Vars  ipmi_channel_ciphers

    Example output:
    ipmi_channel_ciphers:
      [0]:
        [id]:                                         3
        [iana]:                                       N/A
        [auth_alg]:                                   hmac_sha1
        [integrity_alg]:                              hmac_sha1_96
        [confidentiality_alg]:                        aes_cbc_128
      [1]:
        [id]:                                         17
        [iana]:                                       N/A
        [auth_alg]:                                   hmac_sha256
        [integrity_alg]:                              sha256_128
        [confidentiality_alg]:                        aes_cbc_128
    """

    cmd_buf = "channel getciphers ipmi | sed -re 's/ Alg/_Alg/g'"
    stdout, stderr, rc = execute_ipmi_cmd(cmd_buf, "external", print_output=0)
    return vf.outbuf_to_report(stdout)


def get_device_id_config():
    r"""
    Get the device id config data and return as a dictionary.

    Example:

    dev_id_config =  get_device_id_config()
    print_vars(dev_id_config)

    dev_id_config:
        [manuf_id]:            7244
        [addn_dev_support]:     141
        [prod_id]:            16976
        [aux]:                    0
        [id]:                    32
        [revision]:             129
        [device_revision]:        1
    """
    stdout, stderr, rc = bsu.bmc_execute_command("cat /usr/share/ipmi-providers/dev_id.json")

    result = json.loads(stdout)

    # Create device revision field for the user.
    # Reference IPMI specification v2.0 "Get Device ID Command"
    # [7]   1 = device provides Device SDRs
    #       0 = device does not provide Device SDRs
    # [6:4] reserved. Return as 0.
    # [3:0] Device Revision, binary encoded.

    result['device_revision'] = result['revision'] & 0x0F

    return result


def get_chassis_status():
    r"""
    Get IPMI chassis status data and return it as a dictionary.

    The data is obtained by issuing the IPMI "chassis status" command. An
    example is shown below:

    System Power              : off
    Power Overload            : false
    Power Interlock           : inactive
    Main Power Fault          : false
    Power Control Fault       : false
    Power Restore Policy      : previous
    Last Power Event          :
    Chassis Intrusion         : inactive
    Front-Panel Lockout       : inactive
    Drive Fault               : false
    Cooling/Fan Fault         : false
    Sleep Button Disable      : not allowed
    Diag Button Disable       : not allowed
    Reset Button Disable      : not allowed
    Power Button Disable      : allowed
    Sleep Button Disabled     : false
    Diag Button Disabled      : false
    Reset Button Disabled     : false
    Power Button Disabled     : false

    For the data shown above, the following dictionary will be returned.

    chassis_status:
      [system_power]:                        off
      [power_overload]:                      false
      [power_interlock]:                     inactive
      [main_power_fault]:                    false
      [power_control_fault]:                 false
      [power_restore_policy]:                previous
      [last_power_event]:
      [chassis_intrusion]:                   inactive
      [front-panel_lockout]:                 inactive
      [drive_fault]:                         false
      [cooling/fan_fault]:                   false
      [sleep_button_disable]:                not allowed
      [diag_button_disable]:                 not allowed
      [reset_button_disable]:                not allowed
      [power_button_disable]:                allowed
      [sleep_button_disabled]:               false
      [diag_button_disabled]:                false
      [reset_button_disabled]:               false
      [power_button_disabled]:               false
    """

    status, ret_values = \
        grk.run_key_u("Run IPMI Standard Command  chassis status")
    result = vf.key_value_outbuf_to_dict(ret_values, process_indent=1)

    return result
