blob: 961b38087e9916c4e54ce6f4da153633a46c5e0c [file] [log] [blame]
Patrick Venture0ef1faf2018-06-13 12:50:53 -07001#include "dbus/dbuspassive.hpp"
Patrick Ventureda4a5dd2018-08-31 09:42:48 -07002#include "test/dbushelper_mock.hpp"
Patrick Venture0ef1faf2018-06-13 12:50:53 -07003
Patrick Venture0ef1faf2018-06-13 12:50:53 -07004#include <sdbusplus/test/sdbus_mock.hpp>
5#include <string>
6
Patrick Ventureda4a5dd2018-08-31 09:42:48 -07007#include <gmock/gmock.h>
8#include <gtest/gtest.h>
Patrick Venture0ef1faf2018-06-13 12:50:53 -07009
Patrick Ventureda4a5dd2018-08-31 09:42:48 -070010using ::testing::_;
Patrick Venture0ef1faf2018-06-13 12:50:53 -070011using ::testing::InSequence;
12using ::testing::Invoke;
13using ::testing::IsNull;
14using ::testing::NotNull;
15using ::testing::Return;
16using ::testing::StrEq;
Patrick Venture0ef1faf2018-06-13 12:50:53 -070017
18std::string SensorIntf = "xyz.openbmc_project.Sensor.Value";
19
Patrick Ventureda4a5dd2018-08-31 09:42:48 -070020TEST(DbusPassiveTest, FactoryFailsWithInvalidType)
21{
Patrick Venture0ef1faf2018-06-13 12:50:53 -070022 // Verify the type is checked by the factory.
23
24 sdbusplus::SdBusMock sdbus_mock;
25 auto bus_mock = sdbusplus::get_mocked_new(&sdbus_mock);
26 std::string type = "invalid";
27 std::string id = "id";
28
29 DbusHelperMock helper;
30
31 std::unique_ptr<ReadInterface> ri =
32 DbusPassive::CreateDbusPassive(bus_mock, type, id, &helper);
33
34 EXPECT_EQ(ri, nullptr);
35}
36
Patrick Ventureda4a5dd2018-08-31 09:42:48 -070037TEST(DbusPassiveTest, BoringConstructorTest)
38{
Patrick Venture0ef1faf2018-06-13 12:50:53 -070039 // Just build the object, which should be avoided as this does no error
40 // checking at present.
41
42 sdbusplus::SdBusMock sdbus_mock;
43 auto bus_mock = sdbusplus::get_mocked_new(&sdbus_mock);
44 std::string type = "invalid";
45 std::string id = "id";
46 std::string path = "/xyz/openbmc_project/sensors/unknown/id";
47
48 DbusHelperMock helper;
49 EXPECT_CALL(helper, GetService(_, StrEq(SensorIntf), StrEq(path)))
50 .WillOnce(Return("asdf"));
51
Patrick Ventureda4a5dd2018-08-31 09:42:48 -070052 EXPECT_CALL(helper, GetProperties(_, StrEq("asdf"), StrEq(path), NotNull()))
53 .WillOnce(
Patrick Venturee2ec0f62018-09-04 12:30:27 -070054 Invoke([&](sdbusplus::bus::bus& bus, const std::string& service,
55 const std::string& path, struct SensorProperties* prop) {
Patrick Ventureda4a5dd2018-08-31 09:42:48 -070056 prop->scale = -3;
57 prop->value = 10;
58 prop->unit = "x";
59 }));
Patrick Venture0ef1faf2018-06-13 12:50:53 -070060
61 DbusPassive(bus_mock, type, id, &helper);
62 // Success
63}
64
Patrick Ventureda4a5dd2018-08-31 09:42:48 -070065class DbusPassiveTestObj : public ::testing::Test
66{
67 protected:
68 DbusPassiveTestObj() :
69 sdbus_mock(),
70 bus_mock(std::move(sdbusplus::get_mocked_new(&sdbus_mock))), helper()
71 {
72 EXPECT_CALL(helper, GetService(_, StrEq(SensorIntf), StrEq(path)))
73 .WillOnce(Return("asdf"));
Patrick Venture0ef1faf2018-06-13 12:50:53 -070074
Patrick Ventureda4a5dd2018-08-31 09:42:48 -070075 EXPECT_CALL(helper,
76 GetProperties(_, StrEq("asdf"), StrEq(path), NotNull()))
77 .WillOnce(Invoke(
Patrick Venturee2ec0f62018-09-04 12:30:27 -070078 [&](sdbusplus::bus::bus& bus, const std::string& service,
79 const std::string& path, struct SensorProperties* prop) {
Patrick Venture0ef1faf2018-06-13 12:50:53 -070080 prop->scale = _scale;
81 prop->value = _value;
82 prop->unit = "x";
83 }));
84
Patrick Ventureda4a5dd2018-08-31 09:42:48 -070085 ri = DbusPassive::CreateDbusPassive(bus_mock, type, id, &helper);
Patrick Venturee2ec0f62018-09-04 12:30:27 -070086 passive = reinterpret_cast<DbusPassive*>(ri.get());
Patrick Ventureda4a5dd2018-08-31 09:42:48 -070087 EXPECT_FALSE(passive == nullptr);
88 }
Patrick Venture0ef1faf2018-06-13 12:50:53 -070089
Patrick Ventureda4a5dd2018-08-31 09:42:48 -070090 sdbusplus::SdBusMock sdbus_mock;
91 sdbusplus::bus::bus bus_mock;
92 DbusHelperMock helper;
93 std::string type = "temp";
94 std::string id = "id";
95 std::string path = "/xyz/openbmc_project/sensors/temperature/id";
96 int64_t _scale = -3;
97 int64_t _value = 10;
Patrick Venture0ef1faf2018-06-13 12:50:53 -070098
Patrick Ventureda4a5dd2018-08-31 09:42:48 -070099 std::unique_ptr<ReadInterface> ri;
Patrick Venturee2ec0f62018-09-04 12:30:27 -0700100 DbusPassive* passive;
Patrick Venture0ef1faf2018-06-13 12:50:53 -0700101};
102
Patrick Ventureda4a5dd2018-08-31 09:42:48 -0700103TEST_F(DbusPassiveTestObj, ReadReturnsExpectedValues)
104{
Patrick Venture0ef1faf2018-06-13 12:50:53 -0700105 // Verify read is returning the values.
106 ReadReturn v;
107 v.value = 0.01;
108 // TODO: updated is set when the value is created, so we can range check
109 // it.
110 ReadReturn r = passive->read();
111 EXPECT_EQ(v.value, r.value);
112}
113
Patrick Ventureda4a5dd2018-08-31 09:42:48 -0700114TEST_F(DbusPassiveTestObj, SetValueUpdatesValue)
115{
Patrick Venture0ef1faf2018-06-13 12:50:53 -0700116 // Verify setvalue does as advertised.
117
118 double value = 0.01;
119 passive->setValue(value);
120
121 // TODO: updated is set when the value is set, so we can range check it.
122 ReadReturn r = passive->read();
123 EXPECT_EQ(value, r.value);
124}
125
Patrick Ventureda4a5dd2018-08-31 09:42:48 -0700126TEST_F(DbusPassiveTestObj, GetScaleReturnsExpectedValue)
127{
Patrick Venture0ef1faf2018-06-13 12:50:53 -0700128 // Verify the scale is returned as expected.
129 EXPECT_EQ(_scale, passive->getScale());
130}
131
Patrick Ventureda4a5dd2018-08-31 09:42:48 -0700132TEST_F(DbusPassiveTestObj, GetIdReturnsExpectedValue)
133{
Patrick Venture0ef1faf2018-06-13 12:50:53 -0700134 // Verify getId returns the expected value.
135 EXPECT_EQ(id, passive->getId());
136}
137
Patrick Ventureda4a5dd2018-08-31 09:42:48 -0700138TEST_F(DbusPassiveTestObj, VerifyHandlesDbusSignal)
139{
Patrick Venture0ef1faf2018-06-13 12:50:53 -0700140 // The dbus passive sensor listens for updates and if it's the Value
141 // property, it needs to handle it.
142
143 EXPECT_CALL(sdbus_mock, sd_bus_message_ref(IsNull()))
144 .WillOnce(Return(nullptr));
145 sdbusplus::message::message msg(nullptr, &sdbus_mock);
146
Patrick Venturee2ec0f62018-09-04 12:30:27 -0700147 const char* Value = "Value";
Patrick Venture0ef1faf2018-06-13 12:50:53 -0700148 int64_t xValue = 10000;
Patrick Venturee2ec0f62018-09-04 12:30:27 -0700149 const char* intf = "xyz.openbmc_project.Sensor.Value";
Patrick Venture0ef1faf2018-06-13 12:50:53 -0700150 // string, std::map<std::string, sdbusplus::message::variant<int64_t>>
151 // msg.read(msgSensor, msgData);
152
Patrick Ventureda4a5dd2018-08-31 09:42:48 -0700153 EXPECT_CALL(sdbus_mock, sd_bus_message_read_basic(IsNull(), 's', NotNull()))
Patrick Venturee2ec0f62018-09-04 12:30:27 -0700154 .WillOnce(Invoke([&](sd_bus_message* m, char type, void* p) {
155 const char** s = static_cast<const char**>(p);
Patrick Venture0ef1faf2018-06-13 12:50:53 -0700156 // Read the first parameter, the string.
157 *s = intf;
158 return 0;
159 }))
Patrick Venturee2ec0f62018-09-04 12:30:27 -0700160 .WillOnce(Invoke([&](sd_bus_message* m, char type, void* p) {
161 const char** s = static_cast<const char**>(p);
Patrick Venture0ef1faf2018-06-13 12:50:53 -0700162 *s = Value;
163 // Read the string in the pair (dictionary).
164 return 0;
165 }));
166
167 // std::map
168 EXPECT_CALL(sdbus_mock,
169 sd_bus_message_enter_container(IsNull(), 'a', StrEq("{sv}")))
170 .WillOnce(Return(0));
171
172 // while !at_end()
173 EXPECT_CALL(sdbus_mock, sd_bus_message_at_end(IsNull(), 0))
174 .WillOnce(Return(0))
Patrick Ventureda4a5dd2018-08-31 09:42:48 -0700175 .WillOnce(Return(1)); // So it exits the loop after reading one pair.
Patrick Venture0ef1faf2018-06-13 12:50:53 -0700176
177 // std::pair
178 EXPECT_CALL(sdbus_mock,
179 sd_bus_message_enter_container(IsNull(), 'e', StrEq("sv")))
180 .WillOnce(Return(0));
181
182 EXPECT_CALL(sdbus_mock,
183 sd_bus_message_verify_type(IsNull(), 'v', StrEq("x")))
184 .WillOnce(Return(1));
185 EXPECT_CALL(sdbus_mock,
186 sd_bus_message_enter_container(IsNull(), 'v', StrEq("x")))
187 .WillOnce(Return(0));
188
Patrick Ventureda4a5dd2018-08-31 09:42:48 -0700189 EXPECT_CALL(sdbus_mock, sd_bus_message_read_basic(IsNull(), 'x', NotNull()))
Patrick Venturee2ec0f62018-09-04 12:30:27 -0700190 .WillOnce(Invoke([&](sd_bus_message* m, char type, void* p) {
191 int64_t* s = static_cast<int64_t*>(p);
Patrick Venture0ef1faf2018-06-13 12:50:53 -0700192 *s = xValue;
193 return 0;
194 }));
195
196 EXPECT_CALL(sdbus_mock, sd_bus_message_exit_container(IsNull()))
197 .WillOnce(Return(0)) /* variant. */
198 .WillOnce(Return(0)) /* std::pair */
199 .WillOnce(Return(0)); /* std::map */
200
201 int rv = HandleSensorValue(msg, passive);
202 EXPECT_EQ(rv, 0); // It's always 0.
203
204 ReadReturn r = passive->read();
205 EXPECT_EQ(10, r.value);
206}
207
Patrick Ventureda4a5dd2018-08-31 09:42:48 -0700208TEST_F(DbusPassiveTestObj, VerifyIgnoresOtherPropertySignal)
209{
Patrick Venture0ef1faf2018-06-13 12:50:53 -0700210 // The dbus passive sensor listens for updates and if it's the Value
211 // property, it needs to handle it. In this case, it won't be.
212
213 EXPECT_CALL(sdbus_mock, sd_bus_message_ref(IsNull()))
214 .WillOnce(Return(nullptr));
215 sdbusplus::message::message msg(nullptr, &sdbus_mock);
216
Patrick Venturee2ec0f62018-09-04 12:30:27 -0700217 const char* Scale = "Scale";
Patrick Venture0ef1faf2018-06-13 12:50:53 -0700218 int64_t xScale = -6;
Patrick Venturee2ec0f62018-09-04 12:30:27 -0700219 const char* intf = "xyz.openbmc_project.Sensor.Value";
Patrick Venture0ef1faf2018-06-13 12:50:53 -0700220 // string, std::map<std::string, sdbusplus::message::variant<int64_t>>
221 // msg.read(msgSensor, msgData);
222
Patrick Ventureda4a5dd2018-08-31 09:42:48 -0700223 EXPECT_CALL(sdbus_mock, sd_bus_message_read_basic(IsNull(), 's', NotNull()))
Patrick Venturee2ec0f62018-09-04 12:30:27 -0700224 .WillOnce(Invoke([&](sd_bus_message* m, char type, void* p) {
225 const char** s = static_cast<const char**>(p);
Patrick Venture0ef1faf2018-06-13 12:50:53 -0700226 // Read the first parameter, the string.
227 *s = intf;
228 return 0;
229 }))
Patrick Venturee2ec0f62018-09-04 12:30:27 -0700230 .WillOnce(Invoke([&](sd_bus_message* m, char type, void* p) {
231 const char** s = static_cast<const char**>(p);
Patrick Venture0ef1faf2018-06-13 12:50:53 -0700232 *s = Scale;
233 // Read the string in the pair (dictionary).
234 return 0;
235 }));
236
237 // std::map
238 EXPECT_CALL(sdbus_mock,
239 sd_bus_message_enter_container(IsNull(), 'a', StrEq("{sv}")))
240 .WillOnce(Return(0));
241
242 // while !at_end()
243 EXPECT_CALL(sdbus_mock, sd_bus_message_at_end(IsNull(), 0))
244 .WillOnce(Return(0))
Patrick Ventureda4a5dd2018-08-31 09:42:48 -0700245 .WillOnce(Return(1)); // So it exits the loop after reading one pair.
Patrick Venture0ef1faf2018-06-13 12:50:53 -0700246
247 // std::pair
248 EXPECT_CALL(sdbus_mock,
249 sd_bus_message_enter_container(IsNull(), 'e', StrEq("sv")))
250 .WillOnce(Return(0));
251
252 EXPECT_CALL(sdbus_mock,
253 sd_bus_message_verify_type(IsNull(), 'v', StrEq("x")))
254 .WillOnce(Return(1));
255 EXPECT_CALL(sdbus_mock,
256 sd_bus_message_enter_container(IsNull(), 'v', StrEq("x")))
257 .WillOnce(Return(0));
258
Patrick Ventureda4a5dd2018-08-31 09:42:48 -0700259 EXPECT_CALL(sdbus_mock, sd_bus_message_read_basic(IsNull(), 'x', NotNull()))
Patrick Venturee2ec0f62018-09-04 12:30:27 -0700260 .WillOnce(Invoke([&](sd_bus_message* m, char type, void* p) {
261 int64_t* s = static_cast<int64_t*>(p);
Patrick Venture0ef1faf2018-06-13 12:50:53 -0700262 *s = xScale;
263 return 0;
264 }));
265
266 EXPECT_CALL(sdbus_mock, sd_bus_message_exit_container(IsNull()))
267 .WillOnce(Return(0)) /* variant. */
268 .WillOnce(Return(0)) /* std::pair */
269 .WillOnce(Return(0)); /* std::map */
270
271 int rv = HandleSensorValue(msg, passive);
272 EXPECT_EQ(rv, 0); // It's always 0.
273
274 ReadReturn r = passive->read();
275 EXPECT_EQ(0.01, r.value);
276}