blob: dea27e9dc16393d815812ec0f7a231bcc8da9a8c [file] [log] [blame]
Tyler Chatowbf0609c2021-07-31 16:13:27 -07001#include <csignal>
Tyler Chatowa79419d2020-08-12 20:12:11 -07002#include <future>
3#include <thread>
4
5#include "aos/events/ping_generated.h"
6#include "aos/events/pong_generated.h"
Austin Schuh373f1762021-06-02 21:07:09 -07007#include "aos/testing/path.h"
Tyler Chatowa79419d2020-08-12 20:12:11 -07008#include "aos/testing/tmpdir.h"
9#include "gtest/gtest.h"
10#include "starter_rpc_lib.h"
11#include "starterd_lib.h"
12
Austin Schuh373f1762021-06-02 21:07:09 -070013using aos::testing::ArtifactPath;
14
Tyler Chatowa79419d2020-08-12 20:12:11 -070015TEST(StarterdTest, StartStopTest) {
Austin Schuh373f1762021-06-02 21:07:09 -070016 const std::string config_file =
17 ArtifactPath("aos/events/pingpong_config.json");
Tyler Chatowa79419d2020-08-12 20:12:11 -070018
19 aos::FlatbufferDetachedBuffer<aos::Configuration> config =
20 aos::configuration::ReadConfig(config_file);
21
22 const std::string test_dir = aos::testing::TestTmpDir();
23
24 auto new_config = aos::configuration::MergeWithConfig(
25 &config.message(), absl::StrFormat(
26 R"({"applications": [
27 {
28 "name": "ping",
Austin Schuh373f1762021-06-02 21:07:09 -070029 "executable_name": "%s",
Tyler Chatowa79419d2020-08-12 20:12:11 -070030 "args": ["--shm_base", "%s/aos"]
31 },
32 {
33 "name": "pong",
Austin Schuh373f1762021-06-02 21:07:09 -070034 "executable_name": "%s",
Tyler Chatowa79419d2020-08-12 20:12:11 -070035 "args": ["--shm_base", "%s/aos"]
36 }
37 ]})",
Austin Schuh373f1762021-06-02 21:07:09 -070038 ArtifactPath("aos/events/ping"), test_dir,
39 ArtifactPath("aos/events/pong"), test_dir));
Tyler Chatowa79419d2020-08-12 20:12:11 -070040
41 const aos::Configuration *config_msg = &new_config.message();
42
43 // Set up starter with config file
44 aos::starter::Starter starter(config_msg);
45
46 // Create an event loop to watch for ping messages, verifying it actually
47 // started.
48 aos::ShmEventLoop watcher_loop(config_msg);
49 watcher_loop.SkipAosLog();
50
51 watcher_loop
52 .AddTimer([&watcher_loop] {
53 watcher_loop.Exit();
54 FAIL();
55 })
56 ->Setup(watcher_loop.monotonic_now() + std::chrono::seconds(7));
57
58 int test_stage = 0;
59 watcher_loop.MakeWatcher(
60 "/test", [&test_stage, config_msg](const aos::examples::Ping &) {
61 switch (test_stage) {
62 case 1: {
63 test_stage = 2;
64 break;
65 }
66 case 2: {
67 std::thread([config_msg] {
68 LOG(INFO) << "Send command";
69 ASSERT_TRUE(aos::starter::SendCommandBlocking(
70 aos::starter::Command::STOP, "ping", config_msg,
71 std::chrono::seconds(3)));
72 }).detach();
73 test_stage = 3;
74 break;
75 }
76 }
77 });
78
79 watcher_loop.MakeWatcher(
80 "/aos", [&test_stage, &watcher_loop](const aos::starter::Status &status) {
81 const aos::starter::ApplicationStatus *app_status =
82 FindApplicationStatus(status, "ping");
83 if (app_status == nullptr) {
84 return;
85 }
86
87 switch (test_stage) {
88 case 0: {
89 if (app_status->has_state() &&
90 app_status->state() == aos::starter::State::RUNNING) {
91 test_stage = 1;
92 }
93 break;
94 }
95
96 case 3: {
97 if (app_status->has_state() &&
98 app_status->state() == aos::starter::State::STOPPED) {
99 watcher_loop.Exit();
100 SUCCEED();
101 }
102 break;
103 }
104 }
105 });
106
107 std::thread starterd_thread([&starter] { starter.Run(); });
108 watcher_loop.Run();
109
110 starter.Cleanup();
111 starterd_thread.join();
112}
113
114TEST(StarterdTest, DeathTest) {
Austin Schuh373f1762021-06-02 21:07:09 -0700115 const std::string config_file =
116 ArtifactPath("aos/events/pingpong_config.json");
Tyler Chatowa79419d2020-08-12 20:12:11 -0700117
118 aos::FlatbufferDetachedBuffer<aos::Configuration> config =
119 aos::configuration::ReadConfig(config_file);
120
121 const std::string test_dir = aos::testing::TestTmpDir();
122
123 auto new_config = aos::configuration::MergeWithConfig(
124 &config.message(), absl::StrFormat(
125 R"({"applications": [
126 {
127 "name": "ping",
Austin Schuh373f1762021-06-02 21:07:09 -0700128 "executable_name": "%s",
Tyler Chatowa79419d2020-08-12 20:12:11 -0700129 "args": ["--shm_base", "%s/aos"]
130 },
131 {
132 "name": "pong",
Austin Schuh373f1762021-06-02 21:07:09 -0700133 "executable_name": "%s",
Tyler Chatowa79419d2020-08-12 20:12:11 -0700134 "args": ["--shm_base", "%s/aos"]
135 }
136 ]})",
Austin Schuh373f1762021-06-02 21:07:09 -0700137 ArtifactPath("aos/events/ping"), test_dir,
138 ArtifactPath("aos/events/pong"), test_dir));
Tyler Chatowa79419d2020-08-12 20:12:11 -0700139
140 const aos::Configuration *config_msg = &new_config.message();
141
142 // Set up starter with config file
143 aos::starter::Starter starter(config_msg);
144
145 // Create an event loop to watch for ping messages, verifying it actually
146 // started.
147 aos::ShmEventLoop watcher_loop(config_msg);
148 watcher_loop.SkipAosLog();
149
150 watcher_loop
151 .AddTimer([&watcher_loop] {
152 watcher_loop.Exit();
153 FAIL();
154 })
155 ->Setup(watcher_loop.monotonic_now() + std::chrono::seconds(7));
156
157 int test_stage = 0;
158 uint64_t id;
159
160 watcher_loop.MakeWatcher("/aos", [&test_stage, &watcher_loop,
161 &id](const aos::starter::Status &status) {
162 const aos::starter::ApplicationStatus *app_status =
163 FindApplicationStatus(status, "ping");
164 if (app_status == nullptr) {
165 return;
166 }
167
168 switch (test_stage) {
169 case 0: {
170 if (app_status->has_state() &&
171 app_status->state() == aos::starter::State::RUNNING) {
172 test_stage = 1;
173 ASSERT_TRUE(app_status->has_pid());
174 ASSERT_TRUE(kill(app_status->pid(), SIGINT) != -1);
175 ASSERT_TRUE(app_status->has_id());
176 id = app_status->id();
177 }
178 break;
179 }
180
181 case 1: {
182 if (app_status->has_state() &&
183 app_status->state() == aos::starter::State::RUNNING &&
184 app_status->has_id() && app_status->id() != id) {
185 watcher_loop.Exit();
186 SUCCEED();
187 }
188 break;
189 }
190 }
191 });
192
193 std::thread starterd_thread([&starter] { starter.Run(); });
194 watcher_loop.Run();
195
196 starter.Cleanup();
197 starterd_thread.join();
198}