1*** Settings ***
2Documentation  Utilities for fan tests.
3
4Library        ../lib/bmc_ssh_utils.py
5Resource       ../lib/openbmc_ffdc_utils.robot
6Variables      ../data/variables.py
7
8*** Keywords ***
9
10Is Water Cooled
11    [Documentation]  Return 1 if system is water cooled, 0 othersise.
12
13    ${water_cooled}=  Read Attribute
14    ...  ${HOST_INVENTORY_URI}system/chassis  WaterCooled
15    [Return]  ${water_cooled}
16
17
18Get Fan Names
19    [Documentation]  Get the names of the fans marked present in inventory.
20    [Arguments]  ${fan_names}
21    # This keyword populates the fan_names list with the names of
22    # fans present in inventory e.g. fan0, fan2, fan3.
23
24    # Description of Argument(s):
25    # fan_names   The list of fan names to which new fan names are to be
26    #             added to.  This list is returned to the caller.
27
28    ${fan_uris}=  Get Endpoint Paths  ${HOST_INVENTORY_URI}system  fan
29    : FOR  ${fan_uri}  IN  @{fan_uris}
30
31    \  ${fan_properties}=  Read Properties  ${fan_uri}
32    \  ${fan_present}=  Get Variable Value  ${fan_properties['Present']}  0
33    \  ${fan_functional}=  Get Variable Value  ${fan_properties['Functional']}  0
34    \  Continue For Loop If  ${fan_present} == 0 or ${fan_functional} == 0
35    \  ${remaining_uri}  ${fan_name}=  Split Path  ${fan_uri}
36    \  Append To List  ${fan_names}  ${fan_name}
37
38    [Return]  ${fan_names}
39
40
41Verify System Error Indication Due To Fans
42    [Documentation]  Verify enclosure LEDs are on and there's an error log.
43
44    # Both enclosure LEDs should now be On.
45    Verify Front And Rear LED State  On
46
47    # An error log should now exist.
48    Error Logs Should Exist
49
50
51Verify Front And Rear LED State
52    [Documentation]  Check state of the front and rear enclsure fault LEDs.
53    [Arguments]  ${state}
54    # Both LEDs should be in the specified state.  If not fail the test case.
55
56    # Description of Argument(s):
57    # state    The state to check for, either 'Off' or 'On'.
58
59    ${front_fault}=  Get System LED State  front_fault
60    ${rear_fault}=  Get System LED State  rear_fault
61
62    Run Keyword If
63    ...  '${front_fault}' != '${state}' or '${rear_fault}' != '${state}'
64    ...  Fail  msg=Expecting both enclosure LEDs to be ${state}.
65
66
67Set Fan State
68    [Documentation]  Set the fan state, either functional or non-functional.
69    [Arguments]  ${fan_name}  ${fan_state}
70
71    # Description of Argument(s):
72    # fan_name     The name of the fan, e.g. "fan2".
73    # fan_state    The state to set, 1 for functional, 2 for non-functional.
74
75    ${valueDict}=  Create Dictionary  data=${fan_state}
76    Write Attribute
77    ...  ${HOST_INVENTORY_URI}system/chassis/motherboard/${fan_name}
78    ...  Functional  data=${valueDict}
79
80
81Set Fan Target Speed
82    [Documentation]  Set the target speed of a fan.
83    [Arguments]  ${fan_name}  ${fan_speed}
84
85    # Description of argument(s):
86    # fan_name    The name of the fan (e.g. "fan0").
87    # fan_speed   The target speed to set (e.g. "9000").
88
89    ${valueDict}=  Create Dictionary  data=${fan_speed}
90    Write Attribute  ${SENSORS_URI}fan_tach/${fan_name}_0
91    ...  Target  data=${valueDict}
92
93
94Get Target Speed Of Fans
95    [Documentation]  Return the maximum target speed of the system fans.
96
97    ${max_target}=  Set Variable  0
98    ${paths}=  Get Endpoint Paths  ${SENSORS_URI}fan_tach/  0
99    :FOR  ${path}  IN  @{paths}
100    \  ${response}=  OpenBMC Get Request  ${path}
101    \  ${json}=  To JSON  ${response.content}
102    \  ${target_speed}=  Set Variable  ${json["data"]["Target"]}
103    \  ${max_target}=  Run Keyword If  ${target_speed} > ${max_target}
104    ...  Set Variable  ${target_speed}  ELSE  Set Variable  ${max_target}
105    [Return]  ${max_target}
106
107
108Get Target And Blade Speeds
109    [Documentation]  Return the fan target speed setting, the speed of the
110    ...  fan's clockwise blade, and the speed of the counter-clockwise blade.
111    # Each fan unit has two counter-rotating fan blades
112    # One blade is expected to be moving but the other blade may not be
113    # moving whenever the fan unit is transitioning to a new target speed.
114    [Arguments]  ${fan_name}
115
116    # Description of argument(s):
117    # fan_name       The name of a fan (e.g. "fan0")
118
119    # Get the fan target speed and the clockwise blade speed.
120    ${path}=  Catenate  ${SENSORS_URI}fan_tach/${fan_name}_0
121    ${response}=  OpenBMC Get Request  ${path}
122    ${json}=  To JSON  ${response.content}
123    ${fan_clockwise_speed}=  Set Variable  ${json["data"]["Value"]}
124    ${target_speed}=  Set Variable  ${json["data"]["Target"]}
125
126    # Get the counter-clockwise blade speed.
127    ${path}=  Catenate  ${SENSORS_URI}fan_tach/${fan_name}_1
128    ${response}=  OpenBMC Get Request  ${path}
129    ${json}=  To JSON  ${response.content}
130    ${fan_counterclockwise_speed}=  Set Variable  ${json["data"]["Value"]}
131
132    [Return]  ${target_speed}  ${fan_clockwise_speed}
133    ...  ${fan_counterclockwise_speed}
134
135
136Get Fan Target And Speed
137    [Documentation]  Return the fan target speed setting and the
138    ...  speed of the fastest blade.
139    [Arguments]  ${fan_name}
140
141    # Description of argument(s):
142    # fan_name       The name of a fan (e.g. "fan0")
143
144    ${target_speed}  ${clockwise_speed}  ${counterclockwise_speed}=
145    ...  Get Target And Blade Speeds  ${fan_name}
146    ${blade_speed}=  Run Keyword If
147    ...  ${clockwise_speed} > ${counterclockwise_speed}
148    ...  Set Variable  ${clockwise_speed}  ELSE
149    ...  Set Variable  ${counterclockwise_speed}
150    [Return]  ${target_speed}  ${blade_speed}
151
152
153Set Fan Daemon State
154    [Documentation]  Set the state of the fan control service.
155    [Arguments]  ${state}
156
157    # Description of argument(s):
158    # state     The desired state of the service, usually
159    #           "start", "stop", or "restart".
160
161    ${cmd}=  Catenate  systemctl  ${state}  phosphor-fan-control@0.service
162    ${stdout}  ${stderr}  ${rc}=  BMC Execute Command  ${cmd}
163
164
165Verify Minimum Number Of Fans With Cooling Type
166    [Documentation]  Verify minimum number of fans.
167    [Arguments]  ${num_fans}  ${water_cooled}
168
169    # Description of argument(s):
170    # num_fans       The number of fans present in the system.
171    # water_cooled   The value 1 if the system is water cooled,
172    #                0 if air cooled.
173
174    # For a water cooled system.
175    ${min_fans_water}=  Set Variable  2
176
177    # For an air cooled system.
178    ${min_fans_air}=  Set Variable  3
179
180    Rprintn
181    Rpvars  num_fans  water_cooled
182
183    # If water cooled must have at least min_fans_water fans, otherwise
184    # issue Fatal Error and terminate testing.
185    Run Keyword If  ${water_cooled} == 1 and ${num_fans} < ${min_fans_water}
186    ...  Fatal Error
187    ...  msg=Water cooled but less than ${min_fans_water} fans present.
188
189    # If air cooled must have at least min_fans_air fans.
190    Run Keyword If  ${water_cooled} == 0 and ${num_fans} < ${min_fans_air}
191    ...  Fatal Error
192    ...  msg=Air cooled but less than ${min_fans_air} fans present.
193
194
195Verify Fan Monitors With State
196    [Documentation]  Verify fan monitor daemons in the system state.
197    [Arguments]  ${power_state}
198    # The number of monitoring daemons is dependent upon the system
199    # power state.  If power is off there should be 0, if power
200    # is on there should be several.
201
202    # Description of argument(s):
203    # power_state   Power staet of the system, either "On" or "Off"
204
205    ${cmd}=  Catenate  systemctl list-units | grep phosphor-fan | wc -l
206    ${num_fan_daemons}  ${stderr}  ${rc}=  BMC Execute Command  ${cmd}
207
208    Rpvars  power_state  num_fan_daemons
209
210    # Fail if system is On and there are no fan monitors.
211    Run Keyword If  '${power_state}' == 'On' and ${num_fan_daemons} == 0
212    ...  Fail  msg=No phosphor-fan monitors found at power on.
213
214    # Fail if system is Off and the fan monitors are present.
215    Run Keyword If  '${power_state}' == 'Off' and ${num_fan_daemons} != 0
216    ...  Fail  msg=Phosphor-fan monitors found at power off.
217