TEST_F(CoreContextTest, InitiateOrder) { AutoCurrentContext testCtxt; testCtxt->Initiate(); // Initiate inner to outer { auto outerCtxt = testCtxt->Create<void>(); auto middleCtxt = outerCtxt->Create<void>(); auto innerCtxt = middleCtxt->Create<void>(); innerCtxt->Initiate(); middleCtxt->Initiate(); outerCtxt->Initiate(); ASSERT_TRUE(outerCtxt->IsRunning()) << "Context not running after begin initiated"; ASSERT_TRUE(middleCtxt->IsRunning()) << "Context not running after begin initiated"; ASSERT_TRUE(innerCtxt->IsRunning()) << "Context not running after begin initiated"; outerCtxt->SignalShutdown(true); } // Initiate outer to inner { auto outerCtxt = testCtxt->Create<void>(); auto middleCtxt = outerCtxt->Create<void>(); auto innerCtxt = middleCtxt->Create<void>(); outerCtxt->Initiate(); middleCtxt->Initiate(); innerCtxt->Initiate(); ASSERT_TRUE(outerCtxt->IsRunning()) << "Context not running after begin initiated"; ASSERT_TRUE(middleCtxt->IsRunning()) << "Context not running after begin initiated"; ASSERT_TRUE(innerCtxt->IsRunning()) << "Context not running after begin initiated"; outerCtxt->SignalShutdown(true); } // Initiate middle, inner, then outer { auto outerCtxt = testCtxt->Create<void>(); auto middleCtxt = outerCtxt->Create<void>(); auto innerCtxt = middleCtxt->Create<void>(); middleCtxt->Initiate(); innerCtxt->Initiate(); outerCtxt->Initiate(); ASSERT_TRUE(outerCtxt->IsRunning()) << "Context not running after begin initiated"; ASSERT_TRUE(middleCtxt->IsRunning()) << "Context not running after begin initiated"; ASSERT_TRUE(innerCtxt->IsRunning()) << "Context not running after begin initiated"; outerCtxt->SignalShutdown(true); } }
TEST_F(AutoRestarterTest, RestartsOnException) { AutoCurrentContext()->Initiate(); // Use a bolt facility to attach one of our text fixtures: AutoCurrentContext()->BoltTo<ThrowsAnExceptionFirstTime, RestartingSigil>(); // Create our bolt and the restarter AutoRequired<CreationDetectionBolt> bolt; AutoRestarterConfig cfg; cfg.restartOnException = true; cfg.restartOnShutdown = false; cfg.startWhenCreated = true; AutoConstruct<AutoRestarter<RestartingSigil>> restarter(cfg); // Verify the bolt got called: ASSERT_TRUE(bolt->called) << "Bolt was not called even though a context restarter was present in the current context"; // Verify subcontext properties: auto subCtxt = restarter->GetContext(); ASSERT_TRUE(subCtxt != nullptr) << "Restarter did not correctly create a subcontext"; ASSERT_TRUE(subCtxt->Is<RestartingSigil>()) << "Generated subcontext was not marked with the right sigil"; ASSERT_TRUE(subCtxt->IsInitiated()) << "Generated subcontext should have been prospectively started, but was not"; // Terminate the subcontext directly: subCtxt->SignalShutdown(); // Verify that this causes the restarter to release its hold on the subcontext: auto newSubCtxt = restarter->GetContext(); ASSERT_NE(subCtxt, newSubCtxt) << "Restarter did not release a terminated subcontext"; ASSERT_FALSE(newSubCtxt) << "Restarter should not have attempted to create any new contexts on teardown"; }
void AutowiringEnclosure::OnTestEnd(const testing::TestInfo& info) { // Verify we can grab the test case back out and that the pointer is correct: Autowired<TestInfoProxy> ti; Autowired<AutowiringEnclosureExceptionFilter> ecef; auto ctxt = ecef ? ecef->GetContext() : nullptr; // Unconditionally reset the global context as the current context AutoGlobalContext()->SetCurrent(); // Global initialization tests are special, we don't bother checking closure principle on them: if(!strcmp("GlobalInitTest", info.test_case_name())) return; // Need to make sure we got back our exception filter before continuing: ASSERT_TRUE(ecef.IsAutowired()) << "Failed to find the enclosed context exception filter; unit test may have incorrectly reset the enclosing context before returning"; // Now try to tear down the test context enclosure: ctxt->SignalShutdown(); // Do not allow teardown to take more than 250 milliseconds or so if(!ctxt->Wait(std::chrono::milliseconds(250))) { // Critical error--took too long to tear down assert(false); } static const char s_autothrow[] = "AUTOTHROW_"; if(!strncmp(s_autothrow, info.name(), ARRAYCOUNT(s_autothrow) - 1)) // Throw expected, end here return; // If an exception occurred somewhere, report it: ASSERT_FALSE(ecef->m_excepted) << "An unhandled exception occurred in this context" << std::endl << "[" << (ecef->m_ti ? ecef->m_ti->name() : "unknown") << "] " << ecef->m_what; }
/* Loop, synchronously processing requests from clients. */ static void ClientLoop(void) { int i, sts; int maxFd; __pmFdSet readableFds; for (;;) { /* Figure out which file descriptors to wait for input on. Keep * track of the highest numbered descriptor for the select call. */ readableFds = sockFds; maxFd = maxSockFd + 1; sts = __pmSelectRead(maxFd, &readableFds, NULL); if (sts > 0) { if (pmDebug & DBG_TRACE_APPL0) for (i = 0; i <= maxSockFd; i++) if (__pmFD_ISSET(i, &readableFds)) fprintf(stderr, "__pmSelectRead(): from %s fd=%d\n", FdToString(i), i); __pmServerAddNewClients(&readableFds, CheckNewClient); HandleInput(&readableFds); } else if (sts == -1 && neterror() != EINTR) { __pmNotifyErr(LOG_ERR, "ClientLoop select: %s\n", netstrerror()); break; } if (timeToDie) { SignalShutdown(); break; } } }
~EnclosedContextTestBase(void) { // Only attempt teardown if it hasn't already happened: auto ctxt = m_createWeak.lock(); if(!ctxt) return; ctxt->SignalShutdown(); // Do not allow teardown to take more than a millisecond if(!ctxt->Wait(std::chrono::milliseconds(250))) { // Critical error--took too long to tear down assert(false); } }
TEST_F(AutoRestarterTest, RestartsOnShutdown) { AutoCurrentContext()->Initiate(); // Create the restarter AutoRestarterConfig cfg; cfg.restartOnShutdown = true; cfg.startWhenCreated = true; AutoConstruct<AutoRestarter<RestartingSigil>> restarter(cfg); // Terminate the restarter's subcontext: auto subCtxt = restarter->GetContext(); subCtxt->SignalShutdown(); // New context should be created immediately ASSERT_NE(subCtxt, restarter->GetContext()) << "Restarter incorrectly held original context beyond shutdown"; ASSERT_TRUE(restarter->GetContext() != nullptr) << "Restarter did not correctly generate a new context after termination"; }
static void SigIntProc(int s) { SignalShutdown(); }
TEST_F(CoreContextTest, InitiateMultipleChildren) { AutoCurrentContext testCtxt; testCtxt->Initiate(); // Initiate all children { auto outerCtxt = testCtxt->Create<void>(); auto child1 = outerCtxt->Create<void>(); auto child2 = outerCtxt->Create<void>(); auto child3 = outerCtxt->Create<void>(); child1->Initiate(); child2->Initiate(); child3->Initiate(); outerCtxt->Initiate(); ASSERT_TRUE(child1->IsRunning()); ASSERT_TRUE(child2->IsRunning()); ASSERT_TRUE(child3->IsRunning()); outerCtxt->SignalShutdown(true); } // Don't initiate middle child { auto outerCtxt = testCtxt->Create<void>(); auto child1 = outerCtxt->Create<void>(); auto child2 = outerCtxt->Create<void>(); auto child3 = outerCtxt->Create<void>(); child1->Initiate(); child3->Initiate(); outerCtxt->Initiate(); ASSERT_TRUE(child1->IsRunning()); ASSERT_FALSE(child2->IsInitiated()); ASSERT_TRUE(child3->IsRunning()); outerCtxt->SignalShutdown(true); } // Don't initiate middle child and initiate parent first { auto outerCtxt = testCtxt->Create<void>(); auto child1 = outerCtxt->Create<void>(); auto child2 = outerCtxt->Create<void>(); auto child3 = outerCtxt->Create<void>(); outerCtxt->Initiate(); child1->Initiate(); child3->Initiate(); ASSERT_TRUE(child1->IsRunning()); ASSERT_FALSE(child2->IsInitiated()); ASSERT_TRUE(child3->IsRunning()); outerCtxt->SignalShutdown(true); } }
static void ClientLoop(void) { int i, fd, sts; int maxFd; int checkAgents; int reload_ns = 0; __pmFdSet readableFds; for (;;) { /* Figure out which file descriptors to wait for input on. Keep * track of the highest numbered descriptor for the select call. */ readableFds = clientFds; maxFd = maxClientFd + 1; /* If an agent was not ready, it may send an ERROR PDU to indicate it * is now ready. Add such agents to the list of file descriptors. */ checkAgents = 0; for (i = 0; i < nAgents; i++) { AgentInfo *ap = &agent[i]; if (ap->status.notReady) { fd = ap->outFd; __pmFD_SET(fd, &readableFds); if (fd > maxFd) maxFd = fd + 1; checkAgents = 1; if (pmDebug & DBG_TRACE_APPL0) __pmNotifyErr(LOG_INFO, "not ready: check %s agent on fd %d (max = %d)\n", ap->pmDomainLabel, fd, maxFd); } } sts = __pmSelectRead(maxFd, &readableFds, NULL); if (sts > 0) { if (pmDebug & DBG_TRACE_APPL0) for (i = 0; i <= maxClientFd; i++) if (__pmFD_ISSET(i, &readableFds)) fprintf(stderr, "DATA: from %s (fd %d)\n", FdToString(i), i); __pmServerAddNewClients(&readableFds, CheckNewClient); if (checkAgents) reload_ns = HandleReadyAgents(&readableFds); HandleClientInput(&readableFds); } else if (sts == -1 && neterror() != EINTR) { __pmNotifyErr(LOG_ERR, "ClientLoop select: %s\n", netstrerror()); break; } if (restart) { restart = 0; reload_ns = 1; SignalRestart(); } if (reload_ns) { reload_ns = 0; SignalReloadPMNS(); } if (timeToDie) { SignalShutdown(); break; } if (AgentDied) { AgentDied = 0; for (i = 0; i < nAgents; i++) { if (!agent[i].status.connected) mapdom[agent[i].pmDomainId] = nAgents; } } } }