1 #define BOOST_TEST_MODULE CommandableFragmentGenerator_t
2 #include <boost/test/unit_test.hpp>
4 #include "TRACE/tracemf.h"
5 #define TRACE_NAME "CommandableFragmentGenerator_t"
7 #include "artdaq-core/Data/ContainerFragment.hh"
8 #include "artdaq-core/Data/Fragment.hh"
9 #include "artdaq-core/Utilities/configureMessageFacility.hh"
10 #include "artdaq/DAQdata/Globals.hh"
11 #include "artdaq/Generators/CommandableFragmentGenerator.hh"
13 #define TRACE_REQUIRE_EQUAL(l, r) \
18 TLOG(TLVL_DEBUG) << __LINE__ << ": Checking if " << #l << " (" << (l) << ") equals " << #r << " (" << (r) << ")...YES!"; \
22 TLOG(TLVL_ERROR) << __LINE__ << ": Checking if " << #l << " (" << (l) << ") equals " << #r << " (" << (r) << ")...NO!"; \
24 BOOST_REQUIRE_EQUAL((l), (r)); \
27 #define TRACE_REQUIRE(b) \
32 TLOG(TLVL_DEBUG) << __LINE__ << ": Checking if " << #b << " (" << (b) << ") is true...YES!"; \
36 TLOG(TLVL_ERROR) << __LINE__ << ": Checking if " << #b << " (" << (b) << ") is true...NO!"; \
41 namespace artdaqtest {
42 class CommandableFragmentGeneratorTest;
72 bool getNext_(artdaq::FragmentPtrs& frags)
override;
83 void start()
override;
98 void pause()
override;
139 std::atomic<size_t> fireCount_;
140 std::atomic<bool> hwFail_;
141 artdaq::Fragment::timestamp_t ts_;
142 std::atomic<bool> hw_stop_;
143 std::atomic<uint64_t> enabled_ids_;
147 : CommandableFragmentGenerator(ps)
154 metricMan->initialize(ps.get<fhicl::ParameterSet>(
"metrics", fhicl::ParameterSet()));
155 metricMan->do_start();
160 while (fireCount_ > 0)
163 for (
auto&
id : fragmentIDs())
165 if (
id < 64 && ((enabled_ids_ & (0x1 <<
id)) != 0))
167 TLOG(TLVL_DEBUG) <<
"Adding Fragment with ID " <<
id <<
", SeqID " << ev_counter() <<
", and timestamp " << ts_;
168 frags.emplace_back(
new artdaq::Fragment(ev_counter(),
id, artdaq::Fragment::FirstUserFragmentType, ts_));
188 BOOST_AUTO_TEST_SUITE(CommandableFragmentGenerator_t)
192 artdaq::configureMessageFacility(
"CommandableFragmentGenerator_t");
193 TLOG(TLVL_INFO) <<
"Simple test case BEGIN";
194 fhicl::ParameterSet ps;
195 ps.put<
int>(
"board_id", 1);
196 ps.put<
int>(
"fragment_id", 1);
199 testGen.StartCmd(1, 1, 1);
201 artdaq::FragmentPtrs fps;
202 auto sts = testGen.getNext(fps);
203 TRACE_REQUIRE_EQUAL(sts,
true);
204 TRACE_REQUIRE_EQUAL(fps.size(), 1u);
205 TRACE_REQUIRE_EQUAL(fps.front()->fragmentID(), 1);
206 TRACE_REQUIRE_EQUAL(fps.front()->timestamp(), 1);
207 TRACE_REQUIRE_EQUAL(fps.front()->sequenceID(), 1);
208 TLOG(TLVL_INFO) <<
"Simple test case END";
213 artdaq::configureMessageFacility(
"CommandableFragmentGenerator_t");
214 TLOG(TLVL_INFO) <<
"WaitForStart test case BEGIN";
215 fhicl::ParameterSet ps;
216 ps.put<
int>(
"board_id", 1);
217 ps.put<
int>(
"fragment_id", 1);
220 artdaq::FragmentPtrs fps;
221 auto sts = testGen.getNext(fps);
222 TRACE_REQUIRE_EQUAL(sts,
false);
223 TRACE_REQUIRE_EQUAL(fps.size(), 0u);
226 sts = testGen.getNext(fps);
227 TRACE_REQUIRE_EQUAL(sts,
false);
228 TRACE_REQUIRE_EQUAL(fps.size(), 0u);
230 testGen.StartCmd(2, 1, 1);
232 sts = testGen.getNext(fps);
233 TRACE_REQUIRE_EQUAL(sts,
true);
234 TRACE_REQUIRE_EQUAL(fps.size(), 1u);
235 TRACE_REQUIRE_EQUAL(fps.front()->fragmentID(), 1);
236 TRACE_REQUIRE_EQUAL(fps.front()->timestamp(), 1);
237 TRACE_REQUIRE_EQUAL(fps.front()->sequenceID(), 1);
238 TLOG(TLVL_INFO) <<
"WaitForStart test case END";
243 artdaq::configureMessageFacility(
"CommandableFragmentGenerator_t");
244 TLOG(TLVL_INFO) <<
"StateMachine test case BEGIN";
245 fhicl::ParameterSet ps;
246 ps.put<
int>(
"board_id", 1);
247 ps.put<
int>(
"fragment_id", 1);
250 artdaq::FragmentPtrs fps;
251 auto sts = testGen.getNext(fps);
252 TRACE_REQUIRE_EQUAL(sts,
false);
253 TRACE_REQUIRE_EQUAL(fps.size(), 0u);
256 sts = testGen.getNext(fps);
257 TRACE_REQUIRE_EQUAL(sts,
false);
258 TRACE_REQUIRE_EQUAL(fps.size(), 0u);
260 testGen.StartCmd(2, 1, 1);
262 sts = testGen.getNext(fps);
263 TRACE_REQUIRE_EQUAL(sts,
true);
264 TRACE_REQUIRE_EQUAL(fps.size(), 1u);
265 TRACE_REQUIRE_EQUAL(fps.front()->fragmentID(), 1);
266 TRACE_REQUIRE_EQUAL(fps.front()->timestamp(), 1);
267 TRACE_REQUIRE_EQUAL(fps.front()->sequenceID(), 1);
270 testGen.setFireCount(1);
271 testGen.PauseCmd(1, 1);
272 sts = testGen.getNext(fps);
273 TRACE_REQUIRE_EQUAL(sts,
false);
274 TRACE_REQUIRE_EQUAL(fps.size(), 0u);
276 testGen.ResumeCmd(1, 1);
278 sts = testGen.getNext(fps);
279 TRACE_REQUIRE_EQUAL(sts,
true);
280 TRACE_REQUIRE_EQUAL(fps.size(), 1u);
281 TRACE_REQUIRE_EQUAL(fps.front()->fragmentID(), 1);
282 TRACE_REQUIRE_EQUAL(fps.front()->timestamp(), 2);
283 TRACE_REQUIRE_EQUAL(fps.front()->sequenceID(), 2);
286 testGen.StopCmd(1, 1);
287 sts = testGen.getNext(fps);
288 TRACE_REQUIRE_EQUAL(sts,
false);
289 TRACE_REQUIRE_EQUAL(fps.size(), 0u);
291 testGen.StartCmd(2, 1, 1);
292 sts = testGen.getNext(fps);
293 TRACE_REQUIRE_EQUAL(sts,
true);
294 TRACE_REQUIRE_EQUAL(fps.size(), 0u);
296 testGen.setFireCount(1);
297 sts = testGen.getNext(fps);
298 TRACE_REQUIRE_EQUAL(sts,
true);
299 TRACE_REQUIRE_EQUAL(fps.size(), 1u);
300 TRACE_REQUIRE_EQUAL(fps.front()->fragmentID(), 1);
301 TRACE_REQUIRE_EQUAL(fps.front()->timestamp(), 3);
302 TRACE_REQUIRE_EQUAL(fps.front()->sequenceID(), 1);
305 TLOG(TLVL_INFO) <<
"StateMachine test case END";
310 artdaq::configureMessageFacility(
"CommandableFragmentGenerator_t");
311 TLOG(TLVL_INFO) <<
"MultipleIDs test case BEGIN";
312 fhicl::ParameterSet ps;
313 ps.put<
int>(
"board_id", 1);
314 ps.put<std::vector<int>>(
"fragment_ids", {1, 2, 3});
315 ps.put<
int>(
"generated_fragments_per_event", 3);
318 testGen.StartCmd(3, 1, 1);
320 artdaq::FragmentPtrs fps;
321 auto sts = testGen.getNext(fps);
323 std::map<artdaq::Fragment::fragment_id_t, size_t> ids;
324 TRACE_REQUIRE_EQUAL(sts,
true);
325 TRACE_REQUIRE_EQUAL(fps.size(), 3u);
326 while (fps.size() > 0)
328 ids[fps.front()->fragmentID()]++;
329 TRACE_REQUIRE_EQUAL(fps.front()->timestamp(), 1);
330 TRACE_REQUIRE_EQUAL(fps.front()->sequenceID(), 1);
334 TRACE_REQUIRE_EQUAL(ids[1], 1);
335 TRACE_REQUIRE_EQUAL(ids[2], 1);
336 TRACE_REQUIRE_EQUAL(ids[3], 1);
341 testGen.setEnabledIds(0x6);
342 testGen.setFireCount(1);
344 sts = testGen.getNext(fps);
346 TRACE_REQUIRE_EQUAL(sts,
true);
347 TRACE_REQUIRE_EQUAL(fps.size(), 2u);
350 ids[fps.front()->fragmentID()]++;
351 TRACE_REQUIRE_EQUAL(fps.front()->timestamp(), 2);
352 TRACE_REQUIRE_EQUAL(fps.front()->sequenceID(), 2);
355 TRACE_REQUIRE_EQUAL(ids[1], 1);
356 TRACE_REQUIRE_EQUAL(ids[2], 1);
357 TRACE_REQUIRE_EQUAL(ids[3], 0);
359 TLOG(TLVL_INFO) <<
"MultipleIDs test case END";
364 artdaq::configureMessageFacility(
"CommandableFragmentGenerator_t");
365 TLOG(TLVL_INFO) <<
"HardwareFailure_NonThreaded test case BEGIN";
366 fhicl::ParameterSet ps;
367 ps.put<
int>(
"board_id", 1);
368 ps.put<
int>(
"fragment_id", 1);
369 ps.put<
bool>(
"separate_data_thread",
false);
370 ps.put<
bool>(
"separate_monitoring_thread",
false);
371 ps.put<int64_t>(
"hardware_poll_interval_us", 10);
373 auto buffer = std::make_shared<artdaq::RequestBuffer>();
374 buffer->setRunning(
true);
379 artdaq::FragmentPtrs fps;
381 TRACE_REQUIRE_EQUAL(sts,
true);
382 TRACE_REQUIRE_EQUAL(fps.size(), 1u);
383 TRACE_REQUIRE_EQUAL(fps.front()->fragmentID(), 1);
384 TRACE_REQUIRE_EQUAL(fps.front()->timestamp(), 1);
385 TRACE_REQUIRE_EQUAL(fps.front()->sequenceID(), 1);
392 TRACE_REQUIRE_EQUAL(sts,
false);
393 TRACE_REQUIRE(fps.empty());
397 TLOG(TLVL_INFO) <<
"HardwareFailure_NonThreaded test case END";
402 artdaq::configureMessageFacility(
"CommandableFragmentGenerator_t");
403 TLOG(TLVL_INFO) <<
"HardwareFailure_Threaded test case BEGIN";
404 fhicl::ParameterSet ps;
405 ps.put<
int>(
"board_id", 1);
406 ps.put<
int>(
"fragment_id", 1);
407 ps.put<
bool>(
"separate_monitoring_thread",
true);
408 ps.put<int64_t>(
"hardware_poll_interval_us", 750000);
410 auto buffer = std::make_shared<artdaq::RequestBuffer>();
411 buffer->setRunning(
true);
416 artdaq::FragmentPtrs fps;
418 TRACE_REQUIRE_EQUAL(sts,
true);
419 TRACE_REQUIRE_EQUAL(fps.size(), 1u);
420 TRACE_REQUIRE_EQUAL(fps.front()->fragmentID(), 1);
421 TRACE_REQUIRE_EQUAL(fps.front()->timestamp(), 1);
422 TRACE_REQUIRE_EQUAL(fps.front()->sequenceID(), 1);
425 TLOG(TLVL_INFO) <<
"Setting failure bit";
430 TLOG(TLVL_INFO) <<
"Checking that failure is reported by getNext";
433 TRACE_REQUIRE_EQUAL(sts,
false);
434 TRACE_REQUIRE(fps.empty());
438 TLOG(TLVL_INFO) <<
"HardwareFailure_Threaded test case END";
441 BOOST_AUTO_TEST_SUITE_END()
bool getNext_(artdaq::FragmentPtrs &frags) override
Generate data and return it to CommandableFragmentGenerator.
void setEnabledIds(uint64_t bitmask)
Set the enabled IDs mask for the Fragment Generator.
CommandableFragmentGenerator derived class for testing.
void StopCmd(uint64_t timeout, uint64_t timestamp)
Stop the CommandableFragmentGenerator.
CommandableFragmentGeneratorTest(const fhicl::ParameterSet &ps)
CommandableFragmentGeneratorTest Constructor.
void StartCmd(int run, uint64_t timeout, uint64_t timestamp)
Start the CommandableFragmentGenerator.
bool getNext(FragmentPtrs &output) overridefinal
getNext calls either applyRequests or getNext_ to get any data that is ready to be sent to the EventB...
bool checkHWStatus_() override
Returns whether the hwFail flag has not been set.
void stopNoMutex() override
Perform immediate stop actions. No-Op.
void start() override
Perform start actions. No-Op.
CommandableFragmentGenerator is a FragmentGenerator-derived abstract class that defines the interface...
void resume() override
Perform resume actions. No-Op.
void pause() override
Perform pause actions. No-Op.
void setHwFail()
Set the hwFail flag.
void setTimestamp(artdaq::Fragment::timestamp_t ts)
Set the timestamp to be used for the next Fragment.
artdaq::Fragment::timestamp_t getTimestamp()
Get the timestamp that will be used for the next Fragment.
void stop() override
Perform stop actions. No-Op.
void SetRequestBuffer(std::shared_ptr< RequestBuffer > buffer)
Set the shared_ptr to the RequestBuffer.
void joinThreads()
Join any data-taking threads. Should be called when destructing CommandableFragmentGenerator.
void setFireCount(size_t count)
Have getNext_ generate count fragments.