25 profiling_map_[
"setup"] = 0.;
26 profiling_map_[
"hits"] = 0.;
27 profiling_map_[
"seeds"] = 0.;
28 profiling_map_[
"ckf_setup"] = 0.;
29 profiling_map_[
"ckf_run"] = 0.;
30 profiling_map_[
"result_loop"] = 0.;
33 Acts::Vector3 b_field(0., 0., bfield_ * Acts::UnitConstants::T);
36 const auto constBField = std::make_shared<Acts::ConstantBField>(b_field);
44 surf_rotation = Acts::RotationMatrix3::Zero();
46 surf_rotation(1, 0) = 1;
48 surf_rotation(2, 1) = 1;
50 surf_rotation(0, 2) = 1;
52 Acts::Vector3 target_pos(0., 0., 0.);
53 Acts::Translation3 target_translation(target_pos);
54 Acts::Transform3 target_transform(target_translation * surf_rotation);
58 Acts::Surface::makeShared<Acts::PlaneSurface>(target_transform);
61 bool debugTransform =
false;
62 auto transformPos = [
this, debugTransform](
const Acts::Vector3& pos) {
63 Acts::Vector3 rot_pos;
66 rot_pos(2) = pos(0) + DIPOLE_OFFSET;
69 rot_pos(0) += this->map_offset_[0];
70 rot_pos(1) += this->map_offset_[1];
71 rot_pos(2) += this->map_offset_[2];
77 std::cout <<
"PF::DEFAULT3 TRANSFORM" << std::endl;
78 std::cout <<
"PF::Check:: transforming Pos" << std::endl;
79 std::cout << pos << std::endl;
80 std::cout <<
"TO" << std::endl;
81 std::cout << rot_pos << std::endl;
87 Acts::RotationMatrix3 rotation = Acts::RotationMatrix3::Identity();
90 auto transformBField = [rotation, scale, debugTransform](
91 const Acts::Vector3& field,
92 const Acts::Vector3& ) {
94 Acts::Vector3 rot_field;
95 rot_field(0) = field(2);
96 rot_field(1) = field(0);
97 rot_field(2) = field(1);
100 rot_field = scale * rot_field;
103 rot_field = rotation * rot_field;
106 if (debugTransform) {
107 std::cout <<
"PF::DEFAULT3 TRANSFORM" << std::endl;
108 std::cout <<
"PF::Check:: transforming" << std::endl;
109 std::cout << field << std::endl;
110 std::cout <<
"TO" << std::endl;
111 std::cout << rot_field << std::endl;
118 const auto map = std::make_shared<InterpolatedMagneticField3>(
119 loadDefaultBField(field_map_,
122 transformPos, transformBField));
124 auto acts_loggingLevel = Acts::Logging::FATAL;
125 if (debug_acts_) acts_loggingLevel = Acts::Logging::VERBOSE;
128 const auto stepper = Acts::EigenStepper<>{map};
129 const auto const_stepper = Acts::EigenStepper<>{constBField};
130 const auto multi_stepper = Acts::MultiEigenStepperLoop{map};
133 Acts::Navigator::Config navCfg{geometry().getTG()};
134 navCfg.resolveMaterial =
true;
135 navCfg.resolvePassive =
true;
136 navCfg.resolveSensitive =
true;
137 const Acts::Navigator navigator(navCfg);
142 ? std::make_unique<CkfPropagator>(const_stepper, navigator)
143 : std::make_unique<CkfPropagator>(
145 Acts::getDefaultLogger(
"ACTS_PROP", acts_loggingLevel));
148 ckf_ = std::make_unique<std::decay_t<
decltype(*ckf_)>>(
149 *propagator_, Acts::getDefaultLogger(
"CKF", acts_loggingLevel));
150 trk_extrap_ = std::make_shared<std::decay_t<
decltype(*trk_extrap_)>>(
151 *propagator_, geometry_context(), magnetic_field_context());
161 std::vector<ldmx::Track> tracks;
163 auto start = std::chrono::high_resolution_clock::now();
166 if (nevents_ % 1000 == 0) ldmx_log(info) <<
"events processed:" << nevents_;
168 auto loggingLevel = Acts::Logging::DEBUG;
170 Acts::getDefaultLogger(
"LDMX Tracking Geometry Maker", loggingLevel));
173 Acts::PropagatorOptions<Acts::StepperPlainOptions,
174 Acts::NavigatorPlainOptions, ActionList, AbortList>
175 propagator_options(geometry_context(), magnetic_field_context());
177 propagator_options.pathLimit = std::numeric_limits<double>::max();
179 propagator_options.loopProtection =
184 propagator_options.actionList.get<Acts::MaterialInteractor>();
185 mInteractor.multipleScattering =
true;
186 mInteractor.energyLoss =
true;
187 mInteractor.recordInteractions =
false;
191 propagator_options.actionList.get<Acts::detail::SteppingLogger>();
192 sLogger.sterile =
true;
194 propagator_options.stepping.maxStepSize =
195 propagator_step_size_ * Acts::UnitConstants::mm;
196 propagator_options.maxSteps = propagator_maxSteps_;
206 auto setup = std::chrono::high_resolution_clock::now();
207 profiling_map_[
"setup"] +=
208 std::chrono::duration<double, std::milli>(setup - start).count();
210 const std::vector<ldmx::Measurement> measurements =
214 std::shared_ptr<tracking::sim::TruthMatchingTool> truthMatchingTool =
nullptr;
215 std::map<int, ldmx::SimParticle> particleMap;
217 if (event.
exists(
"SimParticles")) {
218 ldmx_log(debug) <<
"Setting up track truth matching tool";
220 truthMatchingTool = std::make_shared<tracking::sim::TruthMatchingTool>(
221 particleMap, measurements);
226 const auto geoId_sl_map = makeGeoIdSourceLinkMap(tg, measurements);
228 auto hits = std::chrono::high_resolution_clock::now();
229 profiling_map_[
"hits"] +=
230 std::chrono::duration<double, std::milli>(hits - setup).count();
236 ldmx_log(debug) <<
"Retrieve the seeds::" << seed_coll_name_;
238 const std::vector<ldmx::Track> seed_tracks =
241 ldmx_log(debug) <<
"Number of seeds::" << seed_tracks.size();
244 std::vector<Acts::BoundTrackParameters> startParameters;
247 std::vector<int> seedPDGID;
249 for (
auto& seed : seed_tracks) {
251 std::shared_ptr<Acts::PerigeeSurface> perigeeSurface =
252 Acts::Surface::makeShared<Acts::PerigeeSurface>(Acts::Vector3(
253 seed.getPerigeeX(), seed.getPerigeeY(), seed.getPerigeeZ()));
255 Acts::BoundVector paramVec;
256 paramVec << seed.getD0(), seed.getZ0(), seed.getPhi(), seed.getTheta(),
257 seed.getQoP(), seed.getT();
259 Acts::BoundSquareMatrix covMat =
260 tracking::sim::utils::unpackCov(seed.getPerigeeCov());
262 ldmx_log(debug) <<
"perigee" << std::endl
263 << seed.getPerigeeX() <<
" " << seed.getPerigeeY() <<
" "
264 << seed.getPerigeeZ() << std::endl
265 <<
"start Parameters" << std::endl
268 ldmx_log(debug) <<
"cov matrix" << std::endl << covMat << std::endl;
271 auto partHypo{Acts::SinglyChargedParticleHypothesis::electron()};
272 startParameters.push_back(
273 Acts::BoundTrackParameters(perigeeSurface, paramVec, covMat, partHypo));
275 seedPDGID.push_back(seed.getPdgID());
280 if (startParameters.size() < 1) {
281 std::vector<ldmx::Track> empty;
282 event.add(out_trk_collection_, empty);
286 auto seeds = std::chrono::high_resolution_clock::now();
287 profiling_map_[
"seeds"] +=
288 std::chrono::duration<double, std::milli>(seeds - hits).count();
290 Acts::GainMatrixUpdater kfUpdater;
295 Acts::MeasurementSelector::Config measurementSelectorCfg = {
297 {Acts::GeometryIdentifier(), {{}, {outlier_pval_}, {1u}}},
300 Acts::MeasurementSelector measSel{measurementSelectorCfg};
304 Acts::CombinatorialKalmanFilterExtensions<TrackContainer> ckf_extensions;
306 if (use1Dmeasurements_)
307 ckf_extensions.calibrator
309 Acts::VectorMultiTrajectory>>(&calibrator);
312 ckf_extensions.calibrator
314 Acts::VectorMultiTrajectory>>(&calibrator);
316 ckf_extensions.updater.connect<
317 &Acts::GainMatrixUpdater::operator()<Acts::VectorMultiTrajectory>>(
320 ckf_extensions.measurementSelector
321 .connect<&Acts::MeasurementSelector::select<Acts::VectorMultiTrajectory>>(
324 ldmx_log(debug) <<
"SourceLinkAccessor..." << std::endl;
327 struct SourceLinkAccIt {
328 using BaseIt =
decltype(geoId_sl_map.begin());
331#pragma GCC diagnostic push
332#pragma GCC diagnostic ignored "-Wunused-local-typedefs"
334 using difference_type =
typename BaseIt::difference_type;
335 using iterator_category =
typename BaseIt::iterator_category;
337 using value_type = Acts::SourceLink;
338 using pointer =
typename BaseIt::pointer;
339 using reference = value_type&;
340#pragma GCC diagnostic pop
342 SourceLinkAccIt& operator++() {
346 bool operator==(
const SourceLinkAccIt& other)
const {
347 return it == other.it;
349 bool operator!=(
const SourceLinkAccIt& other)
const {
350 return !(*
this == other);
355 value_type operator*()
const {
return value_type{it->second}; }
358 auto sourceLinkAccessor = [&](
const Acts::Surface& surface)
359 -> std::pair<SourceLinkAccIt, SourceLinkAccIt> {
360 auto [begin, end] = geoId_sl_map.equal_range(surface.geometryId());
361 return {SourceLinkAccIt{begin}, SourceLinkAccIt{end}};
364 Acts::SourceLinkAccessorDelegate<SourceLinkAccIt> sourceLinkAccessorDelegate;
365 sourceLinkAccessorDelegate.connect<&
decltype(sourceLinkAccessor)::operator(),
366 decltype(sourceLinkAccessor)>(
367 &sourceLinkAccessor);
369 ldmx_log(debug) <<
"Surfaces..." << std::endl;
371 std::shared_ptr<const Acts::PerigeeSurface> origin_surface =
372 Acts::Surface::makeShared<Acts::PerigeeSurface>(
373 Acts::Vector3(0., 0., 0.));
375 ldmx_log(debug) <<
"About to run CKF..." << std::endl;
378 auto ckf_setup = std::chrono::high_resolution_clock::now();
379 profiling_map_[
"ckf_setup"] +=
380 std::chrono::duration<double, std::milli>(ckf_setup - seeds).count();
382 auto ckf_run = std::chrono::high_resolution_clock::now();
383 profiling_map_[
"ckf_run"] +=
384 std::chrono::duration<double, std::milli>(ckf_run - ckf_setup).count();
386 Acts::VectorTrackContainer vtc;
387 Acts::VectorMultiTrajectory mtj;
388 Acts::TrackContainer tc{vtc, mtj};
390 for (
size_t trackId = 0u; trackId < startParameters.size(); ++trackId) {
392 if (seedPDGID.at(trackId) != 0) {
397 const Acts::CombinatorialKalmanFilterOptions<SourceLinkAccIt,
399 ckfOptions(TrackingGeometryUser::geometry_context(),
400 TrackingGeometryUser::magnetic_field_context(),
401 TrackingGeometryUser::calibration_context(),
402 sourceLinkAccessorDelegate, ckf_extensions,
403 propagator_options,
true ,
406 ldmx_log(debug) <<
"Running CKF on seed params "
407 << startParameters.at(trackId).parameters().transpose()
409 ldmx_log(debug) <<
"Checking options: multiple scattering = "
410 << ckfOptions.multipleScattering
411 <<
" energy loss = " << ckfOptions.energyLoss;
413 ckf_->findTracks(startParameters.at(trackId), ckfOptions, tc);
414 ldmx_log(debug) <<
"findTracks returned ... checking if ok";
415 if (not results.ok()) {
416 ldmx_log(debug) <<
"CKF Fit failed" << std::endl;
423 auto& tracksFromSeed = results.value();
425 ldmx_log(debug) <<
"number of entries in results " << tracksFromSeed.size();
426 for (
auto& track : tracksFromSeed) {
428 Acts::smoothTrack(geometry_context(), track);
432 ldmx_log(debug) <<
"Found track: nMeas " << track.nMeasurements();
433 ldmx_log(debug) <<
"Track states " << track.nTrackStates();
434 ldmx_log(debug) <<
"chi2 " << track.chi2();
436 for (
const auto ts : track.trackStatesReversed()) {
438 ldmx_log(debug) <<
"Checking Track State at location "
439 << ts.referenceSurface()
440 .transform(geometry_context())
445 ldmx_log(debug) <<
"Smoothed? " << ts.hasSmoothed() << std::endl;
446 if (ts.hasSmoothed()) {
447 ldmx_log(debug) <<
"Parameters \n"
448 << ts.smoothed().transpose() << std::endl;
449 ldmx_log(debug) <<
"Covariance \n"
450 << ts.smoothedCovariance() << std::endl;
454 auto typeFlags = ts.typeFlags();
456 if (typeFlags.test(Acts::TrackStateFlag::MeasurementFlag) &&
457 ts.hasUncalibratedSourceLink()) {
458 ldmx_log(debug) <<
" getting source link for this measurement";
461 ts.getUncalibratedSourceLink()
462 .template get<ActsExamples::IndexSourceLink>();
464 ldmx_log(debug) <<
" looking up this index in measurements list";
466 ldmx_log(debug) <<
"SourceLink Index::" << sl.
index();
467 ldmx_log(debug) <<
"Measurement:\n" << ldmx_meas <<
"\n";
468 ldmx_log(debug) <<
" adding measurement to ldmx::track";
469 trk.addMeasurementIndex(sl.
index());
472 bool success = trk_extrap_->TrackStateAtSurface(
473 track, target_surface, tsAtTarget, ldmx::TrackStateType::AtTarget);
474 ldmx_log(debug) <<
"target extrapolation success??? " << success;
476 ldmx_log(debug) <<
"Successfully obtained TS at target";
477 ldmx_log(debug) <<
"Parameters At Target: \n"
478 << tsAtTarget.params[0] <<
" " << tsAtTarget.params[1]
479 <<
" " << tsAtTarget.params[2] <<
" "
480 << tsAtTarget.params[3] <<
" " << tsAtTarget.params[4];
482 trk.addTrackState(tsAtTarget);
485 <<
"Could not extrapolate to target? Printing track states: ";
486 ldmx_log(info) <<
" nhits = " << track.nMeasurements();
487 for (
const auto ts : track.trackStatesReversed()) {
488 ldmx_log(info) <<
"Smoothed? " << ts.hasSmoothed() << std::endl;
489 if (ts.hasSmoothed()) {
490 ldmx_log(info) <<
"momentum for track state = "
491 << 1 / ts.smoothed()[Acts::eBoundQOverP];
492 ldmx_log(info) <<
"Parameters \n"
493 << ts.smoothed().transpose() << std::endl;
495 ldmx_log(info) <<
"Track state not smoothed?";
498 ldmx_log(info) <<
"...skipping this track...";
509 Acts::BoundTrackParameters boundStateAtTarget =
510 tracking::sim::utils::btp(tsAtTarget, target_surface, 11);
511 track.setReferenceSurface(target_surface);
512 track.parameters() = boundStateAtTarget.parameters();
514 ldmx_log(debug) <<
typeid(track).name();
516 const Acts::BoundVector& track_pars = track.parameters();
518 const Acts::Surface& track_surface = track.referenceSurface();
519 ldmx_log(debug) <<
"Got the parameters, covariance, and perigee surface";
521 ldmx_log(debug) << track_pars[Acts::eBoundLoc0];
522 ldmx_log(debug) << track_pars[Acts::eBoundLoc1];
523 ldmx_log(debug) << track_pars[Acts::eBoundTheta];
524 ldmx_log(debug) << track_pars[Acts::eBoundPhi];
526 <<
"Reference Surface" << std::endl
527 <<
" " << track_surface.transform(geometry_context()).translation()(0)
528 <<
" " << track_surface.transform(geometry_context()).translation()(1)
530 << track_surface.transform(geometry_context()).translation()(2);
532 trk.setPerigeeLocation(
535 trk.setPerigeeCov(tsAtTarget.cov);
537 ldmx_log(debug) <<
"setting chi2 and nHits: " << track.chi2() <<
" "
538 << track.nMeasurements();
539 trk.setChi2(track.chi2());
540 trk.setNhits(track.nMeasurements());
543 trk.setNdf(track.nMeasurements() - 5);
544 trk.setNsharedHits(track.nSharedHits());
546 ldmx_log(debug) <<
"setting track momentum: " << track.momentum();
547 trk.setMomentum(track.momentum()[0], track.momentum()[1],
548 track.momentum()[2]);
550 ldmx_log(debug) <<
"starting extrapolations";
553 const double ECAL_SCORING_PLANE = 240.5;
554 Acts::Vector3 pos(ECAL_SCORING_PLANE, 0., 0.);
555 Acts::Translation3 surf_translation(pos);
556 Acts::Transform3 surf_transform(surf_translation * surf_rotation);
559 const std::shared_ptr<Acts::PlaneSurface> ecal_surface =
560 Acts::Surface::makeShared<Acts::PlaneSurface>(surf_transform);
563 const std::shared_ptr<Acts::Surface> beamOrigin_surface =
564 tracking::sim::utils::unboundSurface(-700);
566 if (taggerTracking_) {
567 ldmx_log(debug) <<
"Beam Origin Extrapolation";
569 success = trk_extrap_->TrackStateAtSurface(
570 track, beamOrigin_surface, tsAtBeamOrigin,
571 ldmx::TrackStateType::AtBeamOrigin);
574 trk.addTrackState(tsAtBeamOrigin);
575 ldmx_log(debug) <<
"Successfully obtained TS at beam origin";
580 if (!taggerTracking_) {
581 ldmx_log(debug) <<
"Ecal Extrapolation";
583 success = trk_extrap_->TrackStateAtSurface(
584 track, ecal_surface, tsAtEcal, ldmx::TrackStateType::AtECAL);
587 trk.addTrackState(tsAtEcal);
588 ldmx_log(debug) <<
"Successfully obtained TS at Ecal";
589 ldmx_log(debug) <<
"Parameters At Ecal: \n"
590 << tsAtEcal.params[0] <<
" " << tsAtEcal.params[1]
591 <<
" " << tsAtEcal.params[2] <<
" "
592 << tsAtEcal.params[3] <<
" " << tsAtEcal.params[4];
597 if (truthMatchingTool) {
598 auto truthInfo = truthMatchingTool->TruthMatch(trk);
599 trk.setTrackID(truthInfo.trackID);
600 trk.setPdgID(truthInfo.pdgID);
601 trk.setTruthProb(truthInfo.truthProb);
605 if (trk.getNhits() > min_hits_ && abs(1. / trk.getQoP()) > 0.05) {
606 tracks.push_back(trk);
612 auto result_loop = std::chrono::high_resolution_clock::now();
613 profiling_map_[
"result_loop"] +=
614 std::chrono::duration<double, std::milli>(result_loop - ckf_run).count();
617 event.add(out_trk_collection_, tracks);
619 auto end = std::chrono::high_resolution_clock::now();
622 auto diff = end - start;
623 processing_time_ += std::chrono::duration<double, std::milli>(diff).count();