1 /**
2 * Copyright © 2020 IBM Corporation
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16 #include "action_environment.hpp"
17 #include "action_error.hpp"
18 #include "compare_presence_action.hpp"
19 #include "device.hpp"
20 #include "i2c_interface.hpp"
21 #include "id_map.hpp"
22 #include "mock_action.hpp"
23 #include "mock_presence_service.hpp"
24 #include "mock_services.hpp"
25 #include "mocked_i2c_interface.hpp"
26
27 #include <exception>
28 #include <memory>
29 #include <stdexcept>
30 #include <utility>
31
32 #include <gmock/gmock.h>
33 #include <gtest/gtest.h>
34
35 using namespace phosphor::power::regulators;
36
37 using ::testing::Return;
38 using ::testing::Throw;
39
TEST(ComparePresenceActionTests,Constructor)40 TEST(ComparePresenceActionTests, Constructor)
41 {
42 ComparePresenceAction action{
43 "/xyz/openbmc_project/inventory/system/chassis/motherboard/cpu3", true};
44 EXPECT_EQ(action.getFRU(),
45 "/xyz/openbmc_project/inventory/system/chassis/motherboard/cpu3");
46 EXPECT_EQ(action.getValue(), true);
47 }
48
TEST(ComparePresenceActionTests,Execute)49 TEST(ComparePresenceActionTests, Execute)
50 {
51 // Test where works: actual value is true.
52 try
53 {
54 // Create mock I2CInterface
55 std::unique_ptr<i2c::MockedI2CInterface> i2cInterface =
56 std::make_unique<i2c::MockedI2CInterface>();
57
58 // Create Device, IDMap, MockServices and ActionEnvironment
59 // Actual value isPresent() is true
60 Device device{
61 "reg1", true,
62 "/xyz/openbmc_project/inventory/system/chassis/motherboard/reg1",
63 std::move(i2cInterface)};
64 IDMap idMap{};
65 idMap.addDevice(device);
66 MockServices services{};
67 MockPresenceService& presenceService =
68 services.getMockPresenceService();
69 EXPECT_CALL(presenceService,
70 isPresent("/xyz/openbmc_project/inventory/system/chassis/"
71 "motherboard/cpu2"))
72 .Times(2)
73 .WillRepeatedly(Return(true));
74 ActionEnvironment env{idMap, "reg1", services};
75
76 // Test where works: expected value is true, return value is true.
77 {
78 ComparePresenceAction action{"/xyz/openbmc_project/inventory/"
79 "system/chassis/motherboard/cpu2",
80 true};
81 EXPECT_EQ(action.execute(env), true);
82 }
83
84 // Test where works: expected value is false, return value is false.
85 {
86 ComparePresenceAction action{"/xyz/openbmc_project/inventory/"
87 "system/chassis/motherboard/cpu2",
88 false};
89 EXPECT_EQ(action.execute(env), false);
90 }
91 }
92 catch (...)
93 {
94 ADD_FAILURE() << "Should not have caught exception.";
95 }
96
97 // Test where actual value is false.
98 try
99 {
100 // Create mock I2CInterface
101 std::unique_ptr<i2c::MockedI2CInterface> i2cInterface =
102 std::make_unique<i2c::MockedI2CInterface>();
103
104 // Create Device, IDMap, MockServices and ActionEnvironment
105 // Actual value isPresent() is false
106 Device device{
107 "reg1", true,
108 "/xyz/openbmc_project/inventory/system/chassis/motherboard/reg1",
109 std::move(i2cInterface)};
110 IDMap idMap{};
111 idMap.addDevice(device);
112 MockServices services{};
113 MockPresenceService& presenceService =
114 services.getMockPresenceService();
115 EXPECT_CALL(presenceService,
116 isPresent("/xyz/openbmc_project/inventory/system/chassis/"
117 "motherboard/cpu2"))
118 .Times(2)
119 .WillRepeatedly(Return(false));
120 ActionEnvironment env{idMap, "reg1", services};
121
122 // Test where works: expected value is true, return value is false.
123 {
124 ComparePresenceAction action{"/xyz/openbmc_project/inventory/"
125 "system/chassis/motherboard/cpu2",
126 true};
127 EXPECT_EQ(action.execute(env), false);
128 }
129
130 // Test where works: expected value is false, return value is true.
131 {
132 ComparePresenceAction action{"/xyz/openbmc_project/inventory/"
133 "system/chassis/motherboard/cpu2",
134 false};
135 EXPECT_EQ(action.execute(env), true);
136 }
137 }
138 catch (...)
139 {
140 ADD_FAILURE() << "Should not have caught exception.";
141 }
142
143 // Test where fails. Reading presence fails.
144 try
145 {
146 // Create mock I2CInterface
147 std::unique_ptr<i2c::MockedI2CInterface> i2cInterface =
148 std::make_unique<i2c::MockedI2CInterface>();
149
150 // Create Device, IDMap, MockServices and ActionEnvironment
151 // PresenceService cannot get the presence
152 Device device{
153 "reg1", true,
154 "/xyz/openbmc_project/inventory/system/chassis/motherboard/reg1",
155 std::move(i2cInterface)};
156 IDMap idMap{};
157 idMap.addDevice(device);
158 MockServices services{};
159 MockPresenceService& presenceService =
160 services.getMockPresenceService();
161 EXPECT_CALL(presenceService,
162 isPresent("/xyz/openbmc_project/inventory/system/chassis/"
163 "motherboard/cpu2"))
164 .Times(1)
165 .WillOnce(Throw(std::runtime_error(
166 "PresenceService cannot get the presence.")));
167
168 ActionEnvironment env{idMap, "reg1", services};
169
170 ComparePresenceAction action{"/xyz/openbmc_project/inventory/"
171 "system/chassis/motherboard/cpu2",
172 true};
173 action.execute(env);
174 ADD_FAILURE() << "Should not have reached this line.";
175 }
176 catch (const ActionError& e)
177 {
178 EXPECT_STREQ(e.what(), "ActionError: compare_presence: { fru: "
179 "/xyz/openbmc_project/inventory/system/chassis/"
180 "motherboard/cpu2, value: true }");
181 try
182 {
183 // Re-throw inner exception from MockPresenceService.
184 std::rethrow_if_nested(e);
185 ADD_FAILURE() << "Should not have reached this line.";
186 }
187 catch (const std::runtime_error& r_error)
188 {
189 EXPECT_STREQ(r_error.what(),
190 "PresenceService cannot get the presence.");
191 }
192 catch (...)
193 {
194 ADD_FAILURE() << "Should not have caught exception.";
195 }
196 }
197 catch (...)
198 {
199 ADD_FAILURE() << "Should not have caught exception.";
200 }
201 }
202
TEST(ComparePresenceActionTests,GetFRU)203 TEST(ComparePresenceActionTests, GetFRU)
204 {
205 ComparePresenceAction action{
206 "/xyz/openbmc_project/inventory/system/chassis/motherboard/cpu2", true};
207 EXPECT_EQ(action.getFRU(),
208 "/xyz/openbmc_project/inventory/system/chassis/motherboard/cpu2");
209 }
210
TEST(ComparePresenceActionTests,GetValue)211 TEST(ComparePresenceActionTests, GetValue)
212 {
213 ComparePresenceAction action{
214 "/xyz/openbmc_project/inventory/system/chassis/motherboard/cpu3",
215 false};
216 EXPECT_EQ(action.getValue(), false);
217 }
218
TEST(ComparePresenceActionTests,ToString)219 TEST(ComparePresenceActionTests, ToString)
220 {
221 ComparePresenceAction action{
222 "/xyz/openbmc_project/inventory/system/chassis/motherboard/cpu2", true};
223 EXPECT_EQ(action.toString(),
224 "compare_presence: { fru: "
225 "/xyz/openbmc_project/inventory/system/chassis/motherboard/cpu2, "
226 "value: true }");
227 }
228