blob: 372824417012f645b2533aa764533b3ebf848d48 [file] [log] [blame]
Vishwanatha Subbanna32c97272017-04-04 14:10:08 +05301#include <iostream>
2#include <sys/types.h>
3#include <chrono>
4#include <string>
5#include <linux/input.h>
6#include <gtest/gtest.h>
7#include "monitor.hpp"
8
9using namespace phosphor::gpio;
10
11// Exit helper. Ideally should be class but need
12// this to be used inside a static method.
13bool completed {};
14
15class GpioTest : public ::testing::Test
16{
17 public:
18 static constexpr auto DEVICE = "/tmp/test_fifo";
19
20 // systemd event handler
21 sd_event* events;
22
23 // Really needed just for the constructor
24 decltype(input_event::code) code = 10;
25
26 // Really needed just for the constructor
27 decltype(input_event::value) value = 10;
28
29 // Need this so that events can be initialized.
30 int rc;
31
32 // Gets called as part of each TEST_F construction
33 GpioTest()
34 : rc(sd_event_default(&events))
35 {
36 // Check for successful creation of event handler
37 EXPECT_GE(rc, 0);
38
39 // FIFO created to simulate data available
40 EXPECT_EQ(0, mknod(DEVICE, S_IFIFO|0666, 0));
41 }
42
43 // Gets called as part of each TEST_F destruction
44 ~GpioTest()
45 {
46 EXPECT_EQ(0, remove(DEVICE));
47
48 events = sd_event_unref(events);
49 EXPECT_EQ(events, nullptr);
50 }
51
52 // Callback handler on data
53 static int callbackHandler(sd_event_source* es, int fd,
54 uint32_t revents, void* userData)
55 {
56 std::cout <<"Event fired" << std::endl;
57 completed = true;
58 return 0;
59 }
60};
61
62/** @brief Makes sure that event never comes for 3 seconds
63 */
64TEST_F(GpioTest, noEventIn3Seconds)
65{
66 using namespace std::chrono;
67
68 phosphor::gpio::EventPtr eventP { events };
69 events = nullptr;
70
71 const std::string emptyTarget = "";
72 Monitor gpio(DEVICE, code, value, emptyTarget,
Vishwanatha Subbannaba8de422017-06-19 15:51:01 +053073 eventP, callbackHandler, false);
Vishwanatha Subbanna32c97272017-04-04 14:10:08 +053074
75 // Waiting 3 seconds and check if the completion status is set
76 int count = 0;
77 while(count < 3)
78 {
79 // Returns -0- on timeout and positive number on dispatch
80 auto sleepTime = duration_cast<microseconds>(seconds(1));
81 if(!sd_event_run(eventP.get(), sleepTime.count()))
82 {
83 count++;
84 }
85 }
86 EXPECT_EQ(false, completed);
87
88 // 3 to cater to another uptick that happens prior to breaking.
89 EXPECT_EQ(3, count);
90}
91
92/** @brief Pump data in the middle and expect the callback to be invoked */
93TEST_F(GpioTest, pumpDataAndExpectCallBack)
94{
95 using namespace std::chrono;
96
97 phosphor::gpio::EventPtr eventP { events };
98 events = nullptr;
99
100 const std::string emptyTarget = "";
101 Monitor gpio(DEVICE, code, value, emptyTarget,
Vishwanatha Subbannaba8de422017-06-19 15:51:01 +0530102 eventP, callbackHandler, false);
Vishwanatha Subbanna32c97272017-04-04 14:10:08 +0530103
104 // Pump the data in the middle
105 int count = 0;
106 while(count < 2 && !completed)
107 {
108 if (count == 1)
109 {
110 auto pumpData = std::string("echo 'foo' > ") + DEVICE;
111 EXPECT_GE(0, system(pumpData.c_str()));
112 }
113
114 // Returns -0- on timeout
115 auto sleepTime = duration_cast<microseconds>(seconds(1));
116 if(!sd_event_run(eventP.get(), sleepTime.count()))
117 {
118 count++;
119 }
120 }
121 EXPECT_EQ(true, completed);
122 EXPECT_EQ(1, count);
123}