Back to home page

EIC code displayed by LXR

 
 

    


File indexing completed on 2026-07-26 08:22:16

0001 /** TRACCC library, part of the ACTS project (R&D line)
0002  *
0003  * (c) 2023-2026 CERN for the benefit of the ACTS project
0004  *
0005  * Mozilla Public License Version 2.0
0006  */
0007 
0008 // Project include(s).
0009 #include "traccc/cuda/fitting/kalman_fitting_algorithm.hpp"
0010 #include "traccc/cuda/utils/make_magnetic_field.hpp"
0011 #include "traccc/cuda/utils/stream_wrapper.hpp"
0012 #include "traccc/definitions/common.hpp"
0013 #include "traccc/definitions/primitives.hpp"
0014 #include "traccc/device/container_d2h_copy_alg.hpp"
0015 #include "traccc/device/container_h2d_copy_alg.hpp"
0016 #include "traccc/examples/make_magnetic_field.hpp"
0017 #include "traccc/fitting/kalman_fitting_algorithm.hpp"
0018 #include "traccc/geometry/detector.hpp"
0019 #include "traccc/geometry/host_detector.hpp"
0020 #include "traccc/io/read_detector.hpp"
0021 #include "traccc/io/read_measurements.hpp"
0022 #include "traccc/io/utils.hpp"
0023 #include "traccc/options/accelerator.hpp"
0024 #include "traccc/options/detector.hpp"
0025 #include "traccc/options/input_data.hpp"
0026 #include "traccc/options/magnetic_field.hpp"
0027 #include "traccc/options/performance.hpp"
0028 #include "traccc/options/program_options.hpp"
0029 #include "traccc/options/track_fitting.hpp"
0030 #include "traccc/options/track_propagation.hpp"
0031 #include "traccc/performance/soa_comparator.hpp"
0032 #include "traccc/performance/timer.hpp"
0033 #include "traccc/resolution/fitting_performance_writer.hpp"
0034 #include "traccc/utils/propagation.hpp"
0035 #include "traccc/utils/seed_generator.hpp"
0036 
0037 // VecMem include(s).
0038 #include <vecmem/memory/cuda/device_memory_resource.hpp>
0039 #include <vecmem/memory/cuda/host_memory_resource.hpp>
0040 #include <vecmem/memory/cuda/managed_memory_resource.hpp>
0041 #include <vecmem/memory/host_memory_resource.hpp>
0042 #include <vecmem/utils/cuda/async_copy.hpp>
0043 #include <vecmem/utils/cuda/stream_wrapper.hpp>
0044 
0045 // System include(s).
0046 #include <cstdlib>
0047 #include <exception>
0048 #include <iomanip>
0049 #include <iostream>
0050 
0051 using namespace traccc;
0052 
0053 // The main routine
0054 //
0055 int main(int argc, char* argv[]) {
0056   std::unique_ptr<const traccc::Logger> ilogger = traccc::getDefaultLogger(
0057       "TracccExampleTruthFittingCuda", traccc::Logging::Level::INFO);
0058   TRACCC_LOCAL_LOGGER(std::move(ilogger));
0059 
0060   // Program options.
0061   traccc::opts::detector detector_opts;
0062   traccc::opts::magnetic_field bfield_opts;
0063   traccc::opts::input_data input_opts;
0064   traccc::opts::track_propagation propagation_opts;
0065   traccc::opts::track_fitting fitting_opts;
0066   traccc::opts::performance performance_opts;
0067   traccc::opts::accelerator accelerator_opts;
0068   traccc::opts::program_options program_opts{
0069       "Truth Track Fitting Using CUDA",
0070       {detector_opts, bfield_opts, input_opts, propagation_opts,
0071        performance_opts, accelerator_opts},
0072       argc,
0073       argv,
0074       logger().cloneWithSuffix("Options")};
0075 
0076   // Memory resources used by the application.
0077   vecmem::host_memory_resource host_mr;
0078   vecmem::cuda::host_memory_resource cuda_host_mr;
0079   vecmem::cuda::managed_memory_resource mng_mr;
0080   vecmem::cuda::device_memory_resource device_mr;
0081   traccc::memory_resource mr{device_mr, &cuda_host_mr};
0082 
0083   // Performance writer
0084   traccc::fitting_performance_writer fit_performance_writer(
0085       traccc::fitting_performance_writer::config{},
0086       logger().clone("FittingPerformanceWriter"));
0087 
0088   // Output Stats
0089   std::size_t n_fitted_tracks = 0;
0090   std::size_t n_fitted_tracks_cuda = 0;
0091 
0092   /*****************************
0093    * Build a geometry
0094    *****************************/
0095 
0096   // B field value
0097   const auto host_field = traccc::details::make_magnetic_field(bfield_opts);
0098   const auto device_field = traccc::cuda::make_magnetic_field(host_field);
0099 
0100   // Read the detector
0101   traccc::host_detector polymorphic_detector;
0102   traccc::io::read_detector(
0103       polymorphic_detector, mng_mr, detector_opts.detector_file,
0104       detector_opts.material_file, detector_opts.grid_file);
0105 
0106   /*****************************
0107    * Do the reconstruction
0108    *****************************/
0109 
0110   // Stream object
0111   vecmem::cuda::stream_wrapper vecmem_stream;
0112   traccc::cuda::stream_wrapper stream{vecmem_stream.stream()};
0113 
0114   // Copy object
0115   vecmem::copy host_copy;
0116   vecmem::cuda::async_copy async_copy{stream.cudaStream()};
0117 
0118   const traccc::detector_buffer detector_buffer =
0119       traccc::buffer_from_host_detector(polymorphic_detector, device_mr,
0120                                         async_copy);
0121 
0122   /// Standard deviations for seed track parameters
0123   static constexpr std::array<double, e_bound_size> stddevs = {
0124       0.03 * traccc::unit<double>::mm,
0125       0.03 * traccc::unit<double>::mm,
0126       0.017,
0127       0.017,
0128       0.001 / traccc::unit<double>::GeV,
0129       1. * traccc::unit<double>::ns};
0130 
0131   // Fitting algorithm object
0132   traccc::fitting_config fit_cfg(fitting_opts);
0133   fit_cfg.propagation = propagation_opts;
0134 
0135   traccc::host::kalman_fitting_algorithm host_fitting(
0136       fit_cfg, host_mr, host_copy, logger().clone("HostFittingAlg"));
0137   traccc::cuda::kalman_fitting_algorithm device_fitting(
0138       fit_cfg, mr, async_copy, stream, logger().clone("CudaFittingAlg"));
0139 
0140   traccc::performance::timing_info elapsedTimes;
0141 
0142   // Iterate over events
0143   for (std::size_t event = input_opts.skip;
0144        event < input_opts.events + input_opts.skip; ++event) {
0145     // Truth Track Candidates
0146     traccc::event_data evt_data(
0147         input_opts.directory, event, host_mr, input_opts.use_acts_geom_source,
0148         &polymorphic_detector, input_opts.format, false);
0149 
0150     traccc::edm::measurement_collection::host truth_measurements{host_mr};
0151     traccc::edm::track_container<traccc::default_algebra>::host
0152         truth_track_candidates{host_mr};
0153 
0154     host_detector_visitor<detector_type_list>(
0155         polymorphic_detector, [&]<typename detector_traits_t>(
0156                                   const typename detector_traits_t::host& det) {
0157           typename traccc::seed_generator<
0158               typename detector_traits_t::host>::config seed_cfg{};
0159           seed_cfg.initial_sigmas = stddevs;
0160           // Seed generator
0161           traccc::seed_generator<typename detector_traits_t::host> sg(det,
0162                                                                       seed_cfg);
0163           evt_data.generate_truth_candidates(truth_track_candidates,
0164                                              truth_measurements, sg, host_mr);
0165         });
0166     truth_track_candidates.measurements = vecmem::get_data(truth_measurements);
0167 
0168     // track candidates buffer
0169     auto truth_measurements_buffer =
0170         async_copy.to(vecmem::get_data(truth_measurements), mr.main, mr.host,
0171                       vecmem::copy::type::host_to_device);
0172     traccc::edm::track_container<traccc::default_algebra>::buffer
0173         truth_track_candidates_buffer{
0174             async_copy.to(vecmem::get_data(truth_track_candidates.tracks),
0175                           mr.main, mr.host, vecmem::copy::type::host_to_device),
0176             {},
0177             truth_measurements_buffer};
0178 
0179     // Instantiate cuda containers/collections
0180     traccc::edm::track_container<traccc::default_algebra>::buffer
0181         track_states_cuda_buffer;
0182 
0183     {
0184       traccc::performance::timer t("Track fitting  (cuda)", elapsedTimes);
0185 
0186       // Run fitting
0187       track_states_cuda_buffer = device_fitting(detector_buffer, device_field,
0188                                                 truth_track_candidates_buffer);
0189     }
0190 
0191     traccc::edm::track_container<traccc::default_algebra>::host
0192         track_states_cuda{host_mr};
0193     async_copy(track_states_cuda_buffer.tracks, track_states_cuda.tracks,
0194                vecmem::copy::type::device_to_host)
0195         ->wait();
0196     async_copy(track_states_cuda_buffer.states, track_states_cuda.states,
0197                vecmem::copy::type::device_to_host)
0198         ->wait();
0199 
0200     // CPU container(s)
0201     traccc::host::kalman_fitting_algorithm::output_type track_states{host_mr};
0202 
0203     if (accelerator_opts.compare_with_cpu) {
0204       {
0205         traccc::performance::timer t("Track fitting  (cpu)", elapsedTimes);
0206 
0207         // Run fitting
0208         track_states = host_fitting(
0209             polymorphic_detector, host_field,
0210             traccc::edm::track_container<traccc::default_algebra>::const_data(
0211                 truth_track_candidates));
0212       }
0213     }
0214 
0215     if (accelerator_opts.compare_with_cpu) {
0216       // Show which event we are currently presenting the results for.
0217       std::cout << "===>>> Event " << event << " <<<===" << std::endl;
0218 
0219       // Compare the track parameters made on the host and on the device.
0220       traccc::soa_comparator<
0221           traccc::edm::track_collection<traccc::default_algebra>>
0222           compare_track_fits{
0223               "track fits",
0224               traccc::details::comparator_factory<traccc::edm::track_collection<
0225                   traccc::default_algebra>::const_device::const_proxy_type>{
0226                   truth_track_candidates.measurements,
0227                   truth_track_candidates.measurements,
0228                   vecmem::get_data(track_states.states),
0229                   vecmem::get_data(track_states_cuda.states)}};
0230       compare_track_fits(vecmem::get_data(track_states.tracks),
0231                          vecmem::get_data(track_states_cuda.tracks));
0232     }
0233 
0234     // Statistics
0235     n_fitted_tracks += track_states.tracks.size();
0236     n_fitted_tracks_cuda += track_states_cuda.tracks.size();
0237 
0238     if (performance_opts.run) {
0239       for (unsigned int i = 0; i < track_states_cuda.tracks.size(); i++) {
0240         host_detector_visitor<detector_type_list>(
0241             polymorphic_detector,
0242             [&]<typename detector_traits_t>(
0243                 const typename detector_traits_t::host& det) {
0244               fit_performance_writer.write(track_states_cuda.tracks.at(i),
0245                                            track_states_cuda.states,
0246                                            truth_measurements, det, evt_data);
0247             });
0248       }
0249     }
0250   }
0251 
0252   if (performance_opts.run) {
0253     fit_performance_writer.finalize();
0254   }
0255 
0256   std::cout << "==> Statistics ... " << std::endl;
0257   std::cout << "- created (cuda) " << n_fitted_tracks_cuda << " fitted tracks"
0258             << std::endl;
0259   std::cout << "- created  (cpu) " << n_fitted_tracks << " fitted tracks"
0260             << std::endl;
0261   std::cout << "==>Elapsed times...\n" << elapsedTimes << std::endl;
0262 
0263   return EXIT_SUCCESS;
0264 }