150 const EventContext& ctx = getContext();
156 ATH_MSG_WARNING(
"Didn't receive " << FPGAHits.
key() <<
" on first event; assuming no input events.");
158 SmartIF<IEventProcessor> appMgr{service(
"ApplicationMgr")};
160 ATH_MSG_ERROR(
"Failed to retrieve ApplicationMgr as IEventProcessor");
161 return StatusCode::FAILURE;
163 return appMgr->stopRun();
172 ATH_CHECK( FPGAHits_1st.
record (std::make_unique<FPGATrackSimHitCollection>()));
173 ATH_CHECK( FPGAHits_2nd.
record (std::make_unique<FPGATrackSimHitCollection>()));
174 ATH_CHECK( FPGARoads_1st.
record (std::make_unique<FPGATrackSimRoadCollection>()));
175 ATH_CHECK( FPGAHitsInRoads_1st.
record (std::make_unique<FPGATrackSimHitContainer>()));
178 ATH_CHECK(FPGATracks_1stHandle.
record (std::make_unique<FPGATrackSimTrackCollection>()));
181 ATH_CHECK( FPGAHitsFiltered_1st.
record (std::make_unique<FPGATrackSimHitCollection>()));
184 ATH_CHECK( FPGASpacePoints.
record (std::make_unique<FPGATrackSimClusterCollection>()));
187 if (!
m_evtSel->getSelectedEvent()) {
191 std::vector<FPGATrackSimRoad> roads_1st;
192 std::vector<FPGATrackSimTrack> tracks_1st;
193 auto dataFlowInfo = std::make_unique<FPGATrackSimDataFlowInfo>();
197 return StatusCode::SUCCESS;
209 if (!FPGAEventInfo.
isValid()) {
210 ATH_MSG_ERROR(
"Could not find FPGA Event Info with key " << FPGAEventInfo.
key());
211 return StatusCode::FAILURE;
219 std::vector<std::shared_ptr<const FPGATrackSimHit>> phits_output, phits_all, phits_1st, phits_2nd;
221 std::optional<Athena::Chrono> chronoSplitHits;
222 if constexpr (
enableBenchmark) chronoSplitHits.emplace(
"1st Stage: Split hits to 1st and 2nd stage",
m_chrono.get());
224 phits_1st.reserve(FPGAHits->size());
225 phits_2nd.reserve(FPGAHits->size());
236 for (
auto& hit : phits_1st) {
245 std::optional<Athena::Chrono> chronoSPFormation;
256 for (
auto& hit : phits_2nd) {
264 ATH_MSG_DEBUG(
"1st stage hits: " << phits_1st.size() <<
" 2nd stage hits: " << phits_2nd.size() );
265 if (phits_1st.empty())
return StatusCode::SUCCESS;
268 if (!FPGATruthTracks.
isValid()) {
269 ATH_MSG_ERROR(
"Could not find FPGA Truth Track Collection with key " << FPGATruthTracks.
key());
270 return StatusCode::FAILURE;
275 if (!FPGAOfflineTracks.
isValid()) {
276 ATH_MSG_ERROR(
"Could not find FPGA Offline Track Collection with key " << FPGAOfflineTracks.
key());
277 return StatusCode::FAILURE;
286 const std::vector<FPGATrackSimTruthTrack>& truthtracks = *FPGATruthTracks;
291 auto monitorRoads = [&](
auto& monitor,
const auto& roads) {
292 if (!monitor.empty()) {
293 monitor->fillRoad(roads, truthtracks, nLogicalLayers);
297 std::vector<FPGATrackSimRoad> roads_1st;
299 std::optional<Athena::Chrono> chronoGetRoads;
309 std::optional<Athena::Chrono> chronoRoadFiltering;
311 std::vector<FPGATrackSimRoad> postfilter_roads;
314 roads_1st = std::move(postfilter_roads);
323 std::optional<Athena::Chrono> chronoOverlapRemoval;
333 std::optional<Athena::Chrono> chronoRoadFiltering2;
335 std::vector<FPGATrackSimRoad> postfilter2_roads;
338 roads_1st = std::move(postfilter2_roads);
350 auto monitorTracks = [&](
auto& monitor,
const auto& tracks) {
351 if (monitor.empty())
return;
353 std::vector<const FPGATrackSimTrack*> track_ptrs;
354 track_ptrs.reserve(tracks.size());
356 if constexpr (std::is_pointer_v<
typename std::decay_t<
decltype(tracks)>
::value_type>) {
358 track_ptrs.insert(track_ptrs.end(), tracks.begin(), tracks.end());
361 std::transform(tracks.begin(), tracks.end(), std::back_inserter(track_ptrs), [](
const auto& t) { return &t; });
364 monitor->fillTrack(track_ptrs, truthtracks, 1.e15);
367 std::vector<FPGATrackSimTrack> tracks_1st;
370 std::optional<Athena::Chrono> chronoGettingTracks;
384 for (
const auto& road : roads_1st) {
385 std::vector<FPGATrackSimTrack> tracksForCurrentRoad;
388 std::vector<FPGATrackSimRoad> roadVec = {road};
392 if (!tracksForCurrentRoad.empty()) {
393 auto bestTrackIter = std::min_element(
394 tracksForCurrentRoad.begin(), tracksForCurrentRoad.end(),
396 return a.getChi2ndof() < b.getChi2ndof();
399 if (bestTrackIter != tracksForCurrentRoad.end() && bestTrackIter->getChi2ndof() < 1.e15) {
400 tracks_1st.push_back(*bestTrackIter);
409 ATH_MSG_DEBUG(
"No tracking. Just running dummy road2track algorith");
411 for (
const auto& road : roads_1st) {
412 std::vector<std::shared_ptr<const FPGATrackSimHit>> track_hits;
413 for (
unsigned layer = 0; layer < road.getNLayers(); ++layer) {
414 track_hits.insert(track_hits.end(), road.getHits(layer).begin(), road.getHits(layer).end());
419 for (
size_t ihit = 0; ihit < track_hits.size(); ++ihit) {
422 tracks_1st.push_back(track_cand);
432 for (
auto &track : tracks_1st)
433 track.calculateTruth();
443 std::optional<Athena::Chrono> chronoSetTruthParams;
444 if constexpr (
enableBenchmark) chronoSetTruthParams.emplace(
"1st Stage: Set Track Parameters to Truth",
m_chrono.get());
450 track.setQOverPt(truthtracks.front().getQOverPt());
452 track.setD0(truthtracks.front().getD0());
454 track.setPhi(truthtracks.front().getPhi());
456 track.setZ0(truthtracks.front().getZ0());
458 track.setEta(truthtracks.front().getEta());
467 for (
auto const& road : roads_1st) {
468 auto road_hits = std::make_unique<FPGATrackSimHitCollection>();
469 ATH_MSG_DEBUG(
"Hough Road X Y: " << road.getX() <<
" " << road.getY());
470 for (
size_t l = 0; l < road.getNLayers(); ++l) {
471 for (
const auto& layerH : road.getHits(l)) {
475 FPGAHitsInRoads_1st->push_back(std::move(*road_hits));
476 FPGARoads_1st->push_back(road);
481 std::optional<Athena::Chrono> chronoOverlapRemoval2;
485 std::vector<const FPGATrackSimTrack*> tracks_1st_after_chi2;
486 std::vector<const FPGATrackSimTrack*> tracks_1st_after_overlap;
490 tracks_1st_after_chi2.push_back(&track);
491 if (track.passedOR()) {
492 tracks_1st_after_overlap.push_back(&track);
507 if (truthtracks.size() > 0) {
512 unsigned npasschi2(0);
513 unsigned npasschi2OLR(0);
514 if (tracks_1st.size() > 0) {
517 for (
const auto& track : tracks_1st) {
520 if (track.passedOR()) {
532 for (
const FPGATrackSimTrack& track : tracks_1st) FPGATracks_1stHandle->push_back(track);
536 std::vector<FPGATrackSimRoad> roadsLRT;
537 std::vector<FPGATrackSimTrack> tracksLRT;
540 std::vector<std::shared_ptr<const FPGATrackSimHit>> remainingHits;
543 ATH_MSG_DEBUG(
"Doing hit filtering based on prompt tracks.");
549 ATH_MSG_DEBUG(
"No hit filtering requested; using all hits for LRT.");
550 remainingHits = std::move(phits_1st);
558 auto dataFlowInfo = std::make_unique<FPGATrackSimDataFlowInfo>();
569 SmartIF<IEventProcessor> appMgr{service(
"ApplicationMgr")};
571 ATH_MSG_ERROR(
"Failed to retrieve ApplicationMgr as IEventProcessor");
572 return StatusCode::FAILURE;
583 return StatusCode::SUCCESS;