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) 2021-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/ambiguity_resolution/greedy_ambiguity_resolution_algorithm.hpp"
0010 #include "traccc/clusterization/clusterization_algorithm.hpp"
0011 #include "traccc/cuda/ambiguity_resolution/greedy_ambiguity_resolution_algorithm.hpp"
0012 #include "traccc/cuda/clusterization/clusterization_algorithm.hpp"
0013 #include "traccc/cuda/clusterization/measurement_sorting_algorithm.hpp"
0014 #include "traccc/cuda/finding/combinatorial_kalman_filter_algorithm.hpp"
0015 #include "traccc/cuda/fitting/kalman_fitting_algorithm.hpp"
0016 #include "traccc/cuda/gbts_seeding/gbts_seeding_algorithm.hpp"
0017 #include "traccc/cuda/seeding/seed_parameter_estimation_algorithm.hpp"
0018 #include "traccc/cuda/seeding/silicon_pixel_spacepoint_formation_algorithm.hpp"
0019 #include "traccc/cuda/seeding/triplet_seeding_algorithm.hpp"
0020 #include "traccc/cuda/utils/make_magnetic_field.hpp"
0021 #include "traccc/cuda/utils/stream_wrapper.hpp"
0022 #include "traccc/device/container_d2h_copy_alg.hpp"
0023 #include "traccc/efficiency/seeding_performance_writer.hpp"
0024 #include "traccc/examples/make_magnetic_field.hpp"
0025 #include "traccc/finding/combinatorial_kalman_filter_algorithm.hpp"
0026 #include "traccc/fitting/kalman_fitting_algorithm.hpp"
0027 #include "traccc/gbts_seeding/gbts_seeding_config.hpp"
0028 #include "traccc/geometry/detector.hpp"
0029 #include "traccc/geometry/detector_buffer.hpp"
0030 #include "traccc/geometry/host_detector.hpp"
0031 #include "traccc/io/read_cells.hpp"
0032 #include "traccc/io/read_detector.hpp"
0033 #include "traccc/io/read_detector_description.hpp"
0034 #include "traccc/io/utils.hpp"
0035 #include "traccc/options/accelerator.hpp"
0036 #include "traccc/options/clusterization.hpp"
0037 #include "traccc/options/detector.hpp"
0038 #include "traccc/options/input_data.hpp"
0039 #include "traccc/options/magnetic_field.hpp"
0040 #include "traccc/options/performance.hpp"
0041 #include "traccc/options/program_options.hpp"
0042 #include "traccc/options/track_finding.hpp"
0043 #include "traccc/options/track_fitting.hpp"
0044 #include "traccc/options/track_gbts_seeding.hpp"
0045 #include "traccc/options/track_propagation.hpp"
0046 #include "traccc/options/track_resolution.hpp"
0047 #include "traccc/options/track_seeding.hpp"
0048 #include "traccc/performance/collection_comparator.hpp"
0049 #include "traccc/performance/container_comparator.hpp"
0050 #include "traccc/performance/soa_comparator.hpp"
0051 #include "traccc/performance/timer.hpp"
0052 #include "traccc/seeding/seeding_algorithm.hpp"
0053 #include "traccc/seeding/silicon_pixel_spacepoint_formation_algorithm.hpp"
0054 #include "traccc/seeding/track_params_estimation.hpp"
0055 #include "traccc/utils/propagation.hpp"
0056 
0057 // VecMem include(s).
0058 #include <vecmem/memory/cuda/device_memory_resource.hpp>
0059 #include <vecmem/memory/cuda/host_memory_resource.hpp>
0060 #include <vecmem/memory/host_memory_resource.hpp>
0061 #include <vecmem/utils/cuda/async_copy.hpp>
0062 #include <vecmem/utils/cuda/stream_wrapper.hpp>
0063 
0064 // System include(s).
0065 #include <exception>
0066 #include <iomanip>
0067 #include <iostream>
0068 #include <memory>
0069 
0070 int seq_run(const traccc::opts::detector& detector_opts,
0071             const traccc::opts::magnetic_field& bfield_opts,
0072             const traccc::opts::input_data& input_opts,
0073             const traccc::opts::clusterization& clusterization_opts,
0074             const traccc::opts::track_seeding& seeding_opts,
0075             const traccc::opts::track_gbts_seeding& seeding_gbts_opts,
0076             const traccc::opts::track_finding& finding_opts,
0077             const traccc::opts::track_propagation& propagation_opts,
0078             const traccc::opts::track_resolution& resolution_opts,
0079             const traccc::opts::track_fitting& fitting_opts,
0080             const traccc::opts::performance& performance_opts,
0081             const traccc::opts::accelerator& accelerator_opts,
0082             std::unique_ptr<const traccc::Logger> ilogger, bool usingGBTS) {
0083   TRACCC_LOCAL_LOGGER(std::move(ilogger));
0084 
0085   // Memory resources used by the application.
0086   vecmem::host_memory_resource host_mr;
0087   vecmem::cuda::host_memory_resource cuda_host_mr;
0088   vecmem::cuda::device_memory_resource device_mr;
0089   traccc::memory_resource mr{device_mr, &cuda_host_mr};
0090 
0091   // Host copy object
0092   vecmem::copy host_copy;
0093 
0094   // CUDA types used.
0095   vecmem::cuda::stream_wrapper vecmem_stream;
0096   traccc::cuda::stream_wrapper stream{vecmem_stream.stream()};
0097   vecmem::cuda::async_copy copy{stream.cudaStream()};
0098 
0099   // Construct the detector description object.
0100   traccc::detector_design_description::host host_det_descr{host_mr};
0101   traccc::detector_conditions_description::host host_det_cond{host_mr};
0102   traccc::io::read_detector_description(
0103       host_det_descr, host_det_cond, detector_opts.detector_file,
0104       detector_opts.digitization_file, detector_opts.conditions_file,
0105       traccc::data_format::json);
0106   traccc::detector_design_description::data host_det_descr_data{
0107       vecmem::get_data(host_det_descr)};
0108   traccc::detector_conditions_description::data host_det_cond_data{
0109       vecmem::get_data(host_det_cond)};
0110   traccc::detector_design_description::buffer device_det_descr{
0111       [&]() {
0112         // number of elements in the detector design description
0113         std::vector<unsigned int> sizes(host_det_descr.size());
0114         for (std::size_t i = 0; i < host_det_descr.size(); ++i) {
0115           auto this_design = host_det_descr.at(i);
0116           // now for each element, set the size to the largest size of
0117           // that element across all modules
0118           sizes[i] = std::max(
0119               static_cast<unsigned int>(((this_design.bin_edges_x()).size())),
0120               static_cast<unsigned int>(((this_design.bin_edges_y()).size())));
0121         }
0122         return sizes;
0123       }(),
0124       device_mr, &host_mr, vecmem::data::buffer_type::resizable};
0125   copy.setup(device_det_descr)->wait();
0126   copy(host_det_descr_data, device_det_descr)->wait();
0127 
0128   traccc::detector_conditions_description::buffer device_det_cond{
0129       static_cast<traccc::detector_conditions_description::buffer::size_type>(
0130           host_det_cond.size()),
0131       device_mr};
0132   copy.setup(device_det_cond)->wait();
0133   copy(host_det_cond_data, device_det_cond)->wait();
0134 
0135   // Construct a Detray detector object, if supported by the configuration.
0136   traccc::host_detector host_detector;
0137   traccc::io::read_detector(host_detector, host_mr, detector_opts.detector_file,
0138                             detector_opts.material_file,
0139                             detector_opts.grid_file);
0140   const traccc::detector_buffer device_detector =
0141       traccc::buffer_from_host_detector(host_detector, device_mr, copy);
0142   stream.synchronize();
0143 
0144   // Output stats
0145   uint64_t n_cells = 0;
0146   uint64_t n_measurements = 0;
0147   uint64_t n_measurements_cuda = 0;
0148   uint64_t n_spacepoints = 0;
0149   uint64_t n_spacepoints_cuda = 0;
0150   uint64_t n_seeds = 0;
0151   uint64_t n_seeds_cuda = 0;
0152   uint64_t n_found_tracks = 0;
0153   uint64_t n_found_tracks_cuda = 0;
0154   uint64_t n_ambiguity_free_tracks = 0;
0155   uint64_t n_ambiguity_free_tracks_cuda = 0;
0156   uint64_t n_fitted_tracks = 0;
0157   uint64_t n_fitted_tracks_cuda = 0;
0158 
0159   // Type definitions
0160   using host_spacepoint_formation_algorithm =
0161       traccc::host::silicon_pixel_spacepoint_formation_algorithm;
0162   using device_spacepoint_formation_algorithm =
0163       traccc::cuda::silicon_pixel_spacepoint_formation_algorithm;
0164 
0165   using host_finding_algorithm =
0166       traccc::host::combinatorial_kalman_filter_algorithm;
0167   using device_finding_algorithm =
0168       traccc::cuda::combinatorial_kalman_filter_algorithm;
0169 
0170   using host_fitting_algorithm = traccc::host::kalman_fitting_algorithm;
0171   using device_fitting_algorithm = traccc::cuda::kalman_fitting_algorithm;
0172 
0173   // Algorithm configuration(s).
0174   detray::propagation::config propagation_config(propagation_opts);
0175 
0176   const traccc::seedfinder_config seedfinder_config(seeding_opts);
0177   const traccc::seedfilter_config seedfilter_config(seeding_opts);
0178   const traccc::spacepoint_grid_config spacepoint_grid_config(seeding_opts);
0179 
0180   // GBTS seeding configuration
0181   traccc::gbts_seedfinder_config gbts_config(seeding_gbts_opts);
0182 
0183   traccc::finding_config finding_cfg(finding_opts);
0184   finding_cfg.propagation = propagation_config;
0185 
0186   traccc::host::greedy_ambiguity_resolution_algorithm::config_type
0187       resolution_config(resolution_opts);
0188 
0189   traccc::fitting_config fitting_cfg(fitting_opts);
0190   fitting_cfg.propagation = propagation_config;
0191 
0192   // Constant B field for the track finding and fitting
0193   const traccc::vector3 field_vec(seeding_opts);
0194   const auto host_field = traccc::details::make_magnetic_field(bfield_opts);
0195   const auto device_field = traccc::cuda::make_magnetic_field(
0196       host_field, (accelerator_opts.use_gpu_texture_memory
0197                        ? traccc::cuda::magnetic_field_storage::texture_memory
0198                        : traccc::cuda::magnetic_field_storage::global_memory));
0199 
0200   traccc::host::clusterization_algorithm ca(
0201       host_mr, logger().clone("HostClusteringAlg"));
0202   host_spacepoint_formation_algorithm sf(host_mr,
0203                                          logger().clone("HostSpFormationAlg"));
0204   traccc::host::seeding_algorithm sa(seedfinder_config, spacepoint_grid_config,
0205                                      seedfilter_config, host_mr,
0206                                      logger().clone("HostSeedingAlg"));
0207   traccc::track_params_estimation_config track_params_estimation_config;
0208   traccc::host::track_params_estimation tp(
0209       track_params_estimation_config, host_mr,
0210       logger().clone("HostTrackParEstAlg"));
0211   host_finding_algorithm finding_alg(finding_cfg, host_mr,
0212                                      logger().clone("HostFindingAlg"));
0213   traccc::host::greedy_ambiguity_resolution_algorithm resolution_alg_cpu(
0214       resolution_config, host_mr, logger().clone("HostAmbiguityResolutionAlg"));
0215   host_fitting_algorithm fitting_alg(fitting_cfg, host_mr, host_copy,
0216                                      logger().clone("HostFittingAlg"));
0217 
0218   traccc::cuda::clusterization_algorithm ca_cuda(
0219       mr, copy, stream, clusterization_opts,
0220       logger().clone("CudaClusteringAlg"));
0221   traccc::cuda::measurement_sorting_algorithm ms_cuda(
0222       mr, copy, stream, logger().clone("CudaMeasSortingAlg"));
0223   device_spacepoint_formation_algorithm sf_cuda(
0224       mr, copy, stream, logger().clone("CudaSpFormationAlg"));
0225   traccc::cuda::triplet_seeding_algorithm sa_cuda(
0226       seedfinder_config, spacepoint_grid_config, seedfilter_config, mr, copy,
0227       stream, logger().clone("CudaSeedingAlg"));
0228   traccc::cuda::gbts_seeding_algorithm gbts_sa_cuda(
0229       gbts_config, mr, copy, stream, logger().clone("CudaGbtsSeedingAlg"));
0230   traccc::cuda::seed_parameter_estimation_algorithm tp_cuda(
0231       track_params_estimation_config, mr, copy, stream,
0232       logger().clone("CudaTrackParEstAlg"));
0233   device_finding_algorithm finding_alg_cuda(finding_cfg, mr, copy, stream,
0234                                             logger().clone("CudaFindingAlg"));
0235   traccc::cuda::greedy_ambiguity_resolution_algorithm resolution_alg_cuda(
0236       resolution_config, mr, copy, stream,
0237       logger().clone("CudaAmbiguityResolutionAlg"));
0238   device_fitting_algorithm fitting_alg_cuda(fitting_cfg, mr, copy, stream,
0239                                             logger().clone("CudaFittingAlg"));
0240 
0241   // performance writer
0242   traccc::seeding_performance_writer sd_performance_writer(
0243       traccc::seeding_performance_writer::config{},
0244       logger().clone("SeedingPerformanceWriter"));
0245 
0246   traccc::performance::timing_info elapsedTimes;
0247 
0248   // Loop over events
0249   for (std::size_t event = input_opts.skip;
0250        event < input_opts.events + input_opts.skip; ++event) {
0251     // Instantiate host containers/collections
0252     traccc::host::clusterization_algorithm::output_type measurements_per_event{
0253         host_mr};
0254     host_spacepoint_formation_algorithm::output_type spacepoints_per_event{
0255         host_mr};
0256     traccc::host::seeding_algorithm::output_type seeds{host_mr};
0257     traccc::host::track_params_estimation::output_type params;
0258     host_finding_algorithm::output_type track_candidates{host_mr};
0259     traccc::host::greedy_ambiguity_resolution_algorithm::output_type
0260         res_track_candidates{host_mr};
0261     host_fitting_algorithm::output_type track_states{host_mr};
0262 
0263     // Instantiate cuda containers/collections
0264     traccc::edm::measurement_collection::buffer measurements_cuda_buffer;
0265     traccc::edm::spacepoint_collection::buffer spacepoints_cuda_buffer;
0266     traccc::edm::seed_collection::buffer seeds_cuda_buffer;
0267     traccc::bound_track_parameters_collection_types::buffer params_cuda_buffer(
0268         0, *mr.host);
0269     traccc::edm::track_container<traccc::default_algebra>::buffer
0270         track_candidates_buffer;
0271     traccc::edm::track_container<traccc::default_algebra>::buffer
0272         res_track_candidates_buffer;
0273     traccc::edm::track_container<traccc::default_algebra>::buffer
0274         track_states_buffer;
0275 
0276     {
0277       traccc::performance::timer wall_t("Wall time", elapsedTimes);
0278 
0279       traccc::edm::silicon_cell_collection::host cells_per_event{host_mr};
0280 
0281       {
0282         traccc::performance::timer t("File reading  (cpu)", elapsedTimes);
0283         // Read the cells from the relevant event file into host memory.
0284         static constexpr bool DEDUPLICATE = true;
0285         traccc::io::read_cells(cells_per_event, event, input_opts.directory,
0286                                logger().clone(), &host_det_cond,
0287                                input_opts.format, DEDUPLICATE,
0288                                input_opts.use_acts_geom_source);
0289       }  // stop measuring file reading timer
0290 
0291       n_cells += cells_per_event.size();
0292 
0293       // Create device copy of input collections
0294       traccc::edm::silicon_cell_collection::buffer cells_buffer(
0295           static_cast<unsigned int>(cells_per_event.size()), mr.main);
0296       copy.setup(cells_buffer)->wait();
0297       copy(vecmem::get_data(cells_per_event), cells_buffer)->wait();
0298 
0299       // CUDA
0300       {
0301         traccc::performance::timer t("Clusterization (cuda)", elapsedTimes);
0302         // Reconstruct it into spacepoints on the device.
0303         auto unsorted_measurements =
0304             ca_cuda(cells_buffer, device_det_descr, device_det_cond);
0305         measurements_cuda_buffer = ms_cuda(unsorted_measurements);
0306         stream.synchronize();
0307       }  // stop measuring clusterization cuda timer
0308 
0309       // CPU
0310       if (accelerator_opts.compare_with_cpu) {
0311         traccc::performance::timer t("Clusterization  (cpu)", elapsedTimes);
0312         measurements_per_event = ca(vecmem::get_data(cells_per_event),
0313                                     host_det_descr_data, host_det_cond_data);
0314       }  // stop measuring clusterization cpu timer
0315 
0316       // Perform seeding, track finding and fitting only when using a
0317       // Detray geometry.
0318       // CUDA
0319       {
0320         traccc::performance::timer t("Spacepoint formation (cuda)",
0321                                      elapsedTimes);
0322         spacepoints_cuda_buffer =
0323             sf_cuda(device_detector, measurements_cuda_buffer);
0324         stream.synchronize();
0325       }  // stop measuring spacepoint formation cuda timer
0326 
0327       // CPU
0328       if (accelerator_opts.compare_with_cpu) {
0329         traccc::performance::timer t("Spacepoint formation  (cpu)",
0330                                      elapsedTimes);
0331         spacepoints_per_event =
0332             sf(host_detector, vecmem::get_data(measurements_per_event));
0333       }  // stop measuring spacepoint formation cpu timer
0334 
0335       // CUDA
0336       {
0337         traccc::performance::timer t("Seeding (cuda)", elapsedTimes);
0338         if (usingGBTS) {
0339           seeds_cuda_buffer =
0340               gbts_sa_cuda(spacepoints_cuda_buffer, measurements_cuda_buffer);
0341         } else {
0342           seeds_cuda_buffer = sa_cuda(spacepoints_cuda_buffer);
0343         }
0344         stream.synchronize();
0345       }  // stop measuring seeding cuda timer
0346 
0347       // CPU
0348       if (accelerator_opts.compare_with_cpu) {
0349         traccc::performance::timer t("Seeding  (cpu)", elapsedTimes);
0350         seeds = sa(vecmem::get_data(spacepoints_per_event));
0351       }  // stop measuring seeding cpu timer
0352 
0353       // CUDA
0354       {
0355         traccc::performance::timer t("Track params (cuda)", elapsedTimes);
0356         params_cuda_buffer =
0357             tp_cuda(device_field, measurements_cuda_buffer,
0358                     spacepoints_cuda_buffer, seeds_cuda_buffer);
0359         stream.synchronize();
0360       }  // stop measuring track params timer
0361 
0362       // CPU
0363       if (accelerator_opts.compare_with_cpu) {
0364         traccc::performance::timer t("Track params  (cpu)", elapsedTimes);
0365         params = tp(vecmem::get_data(measurements_per_event),
0366                     vecmem::get_data(spacepoints_per_event),
0367                     vecmem::get_data(seeds), field_vec);
0368       }  // stop measuring track params cpu timer
0369 
0370       // CUDA
0371       {
0372         traccc::performance::timer timer{"Track finding (cuda)", elapsedTimes};
0373         track_candidates_buffer =
0374             finding_alg_cuda(device_detector, device_field,
0375                              measurements_cuda_buffer, params_cuda_buffer);
0376       }
0377 
0378       // CPU
0379       if (accelerator_opts.compare_with_cpu) {
0380         traccc::performance::timer timer{"Track finding (cpu)", elapsedTimes};
0381         track_candidates = finding_alg(host_detector, host_field,
0382                                        vecmem::get_data(measurements_per_event),
0383                                        vecmem::get_data(params));
0384       }
0385 
0386       // CUDA
0387       {
0388         traccc::performance::timer timer{"Ambiguity resolution (cuda)",
0389                                          elapsedTimes};
0390         res_track_candidates_buffer =
0391             resolution_alg_cuda(track_candidates_buffer);
0392       }
0393 
0394       // CPU
0395       if (accelerator_opts.compare_with_cpu) {
0396         traccc::performance::timer timer{"Ambiguity resolution (cpu)",
0397                                          elapsedTimes};
0398         res_track_candidates = resolution_alg_cpu(
0399             traccc::edm::track_container<traccc::default_algebra>::const_data(
0400                 track_candidates));
0401       }
0402 
0403       // CUDA
0404       {
0405         traccc::performance::timer timer{"Track fitting (cuda)", elapsedTimes};
0406         track_states_buffer = fitting_alg_cuda(device_detector, device_field,
0407                                                res_track_candidates_buffer);
0408       }
0409 
0410       // CPU
0411       if (accelerator_opts.compare_with_cpu) {
0412         traccc::performance::timer timer{"Track fitting (cpu)", elapsedTimes};
0413         track_states = fitting_alg(
0414             host_detector, host_field,
0415             traccc::edm::track_container<traccc::default_algebra>::const_data(
0416                 res_track_candidates));
0417       }
0418 
0419     }  // Stop measuring wall time
0420 
0421     /*----------------------------------
0422       compare cpu and cuda result
0423       ----------------------------------*/
0424 
0425     traccc::edm::measurement_collection::host measurements_per_event_cuda{
0426         host_mr};
0427     traccc::edm::spacepoint_collection::host spacepoints_per_event_cuda{
0428         host_mr};
0429     traccc::edm::seed_collection::host seeds_cuda{host_mr};
0430     traccc::bound_track_parameters_collection_types::host params_cuda;
0431     traccc::edm::track_collection<traccc::default_algebra>::host
0432         track_candidates_cuda{host_mr};
0433     traccc::edm::track_collection<traccc::default_algebra>::host
0434         res_track_candidates_cuda{host_mr};
0435     traccc::edm::track_container<traccc::default_algebra>::host
0436         track_states_cuda{host_mr};
0437 
0438     copy(measurements_cuda_buffer, measurements_per_event_cuda)->wait();
0439     copy(spacepoints_cuda_buffer, spacepoints_per_event_cuda)->wait();
0440     copy(seeds_cuda_buffer, seeds_cuda)->wait();
0441     copy(params_cuda_buffer, params_cuda)->wait();
0442     copy(track_candidates_buffer.tracks, track_candidates_cuda,
0443          vecmem::copy::type::device_to_host)
0444         ->wait();
0445     copy(res_track_candidates_buffer.tracks, res_track_candidates_cuda,
0446          vecmem::copy::type::device_to_host)
0447         ->wait();
0448     copy(track_states_buffer.tracks, track_states_cuda.tracks,
0449          vecmem::copy::type::device_to_host)
0450         ->wait();
0451     copy(track_states_buffer.states, track_states_cuda.states,
0452          vecmem::copy::type::device_to_host)
0453         ->wait();
0454     track_states_cuda.measurements =
0455         vecmem::get_data(measurements_per_event_cuda);
0456     stream.synchronize();
0457 
0458     if (accelerator_opts.compare_with_cpu) {
0459       // Show which event we are currently presenting the results for.
0460       TRACCC_INFO("===>>> Event " << event << " <<<===");
0461 
0462       // Compare the measurements made on the host and on the device.
0463       traccc::soa_comparator<traccc::edm::measurement_collection>
0464           compare_measurements{"measurements"};
0465       compare_measurements(vecmem::get_data(measurements_per_event),
0466                            vecmem::get_data(measurements_per_event_cuda));
0467 
0468       // Compare the spacepoints made on the host and on the device.
0469       traccc::soa_comparator<traccc::edm::spacepoint_collection>
0470           compare_spacepoints{"spacepoints"};
0471       compare_spacepoints(vecmem::get_data(spacepoints_per_event),
0472                           vecmem::get_data(spacepoints_per_event_cuda));
0473 
0474       // Compare the seeds made on the host and on the device
0475       traccc::soa_comparator<traccc::edm::seed_collection> compare_seeds{
0476           "seeds",
0477           traccc::details::comparator_factory<
0478               traccc::edm::seed_collection::const_device::const_proxy_type>{
0479               vecmem::get_data(spacepoints_per_event),
0480               vecmem::get_data(spacepoints_per_event_cuda)}};
0481       compare_seeds(vecmem::get_data(seeds), vecmem::get_data(seeds_cuda));
0482 
0483       // Compare the track parameters made on the host and on the device.
0484       traccc::collection_comparator<traccc::bound_track_parameters<>>
0485           compare_track_parameters{"track parameters"};
0486       compare_track_parameters(vecmem::get_data(params),
0487                                vecmem::get_data(params_cuda));
0488 
0489       // Compare tracks found on the host and on the device.
0490       traccc::soa_comparator<
0491           traccc::edm::track_collection<traccc::default_algebra>>
0492           compare_track_candidates{
0493               "track candidates",
0494               traccc::details::comparator_factory<traccc::edm::track_collection<
0495                   traccc::default_algebra>::const_device::const_proxy_type>{
0496                   vecmem::get_data(measurements_per_event),
0497                   vecmem::get_data(measurements_per_event_cuda),
0498                   {},
0499                   {}}};
0500       compare_track_candidates(vecmem::get_data(track_candidates.tracks),
0501                                vecmem::get_data(track_candidates_cuda));
0502 
0503       // Compare tracks resolved on the host and on the device.
0504       traccc::soa_comparator<
0505           traccc::edm::track_collection<traccc::default_algebra>>
0506           compare_resolved_track_candidates{
0507               "resolved track candidates",
0508               traccc::details::comparator_factory<traccc::edm::track_collection<
0509                   traccc::default_algebra>::const_device::const_proxy_type>{
0510                   vecmem::get_data(measurements_per_event),
0511                   vecmem::get_data(measurements_per_event_cuda),
0512                   {},
0513                   {}}};
0514       compare_resolved_track_candidates(
0515           vecmem::get_data(res_track_candidates.tracks),
0516           vecmem::get_data(res_track_candidates_cuda));
0517 
0518       // Compare tracks fitted on the host and on the device.
0519       traccc::soa_comparator<
0520           traccc::edm::track_collection<traccc::default_algebra>>
0521           compare_track_fits{
0522               "track fits",
0523               traccc::details::comparator_factory<traccc::edm::track_collection<
0524                   traccc::default_algebra>::const_device::const_proxy_type>{
0525                   vecmem::get_data(measurements_per_event),
0526                   vecmem::get_data(measurements_per_event_cuda),
0527                   vecmem::get_data(track_states.states),
0528                   vecmem::get_data(track_states_cuda.states)}};
0529       compare_track_fits(vecmem::get_data(track_states.tracks),
0530                          vecmem::get_data(track_states_cuda.tracks));
0531     }
0532     /// Statistics
0533     n_measurements += measurements_per_event.size();
0534     n_spacepoints += spacepoints_per_event.size();
0535     n_seeds += seeds.size();
0536     n_measurements_cuda += measurements_per_event_cuda.size();
0537     n_spacepoints_cuda += spacepoints_per_event_cuda.size();
0538     n_seeds_cuda += seeds_cuda.size();
0539     n_found_tracks += track_candidates.tracks.size();
0540     n_found_tracks_cuda += track_candidates_cuda.size();
0541     n_ambiguity_free_tracks += res_track_candidates.tracks.size();
0542     n_ambiguity_free_tracks_cuda += res_track_candidates_cuda.size();
0543     n_fitted_tracks += track_states.tracks.size();
0544     n_fitted_tracks_cuda += track_states_cuda.tracks.size();
0545 
0546     if (performance_opts.run) {
0547       // TODO: Do evt_data.fill_cca_result(...) with cuda clusters and
0548       // measurements
0549     }
0550   }
0551 
0552   if (performance_opts.run) {
0553     sd_performance_writer.finalize();
0554   }
0555 
0556   TRACCC_INFO("==> Statistics ... ");
0557   TRACCC_INFO("- read    " << n_cells << " cells");
0558   TRACCC_INFO("- created (cpu)  " << n_measurements << " measurements     ");
0559   TRACCC_INFO("- created (cuda)  " << n_measurements_cuda
0560                                    << " measurements     ");
0561   TRACCC_INFO("- created (cpu)  " << n_spacepoints << " spacepoints     ");
0562   TRACCC_INFO("- created (cuda) " << n_spacepoints_cuda << " spacepoints     ");
0563 
0564   TRACCC_INFO("- created  (cpu) " << n_seeds << " seeds");
0565   TRACCC_INFO("- created (cuda) " << n_seeds_cuda << " seeds");
0566   TRACCC_INFO("- found (cpu)    " << n_found_tracks << " tracks");
0567   TRACCC_INFO("- found (cuda)   " << n_found_tracks_cuda << " tracks");
0568   TRACCC_INFO("- resolved (cpu)    " << n_ambiguity_free_tracks << " tracks");
0569   TRACCC_INFO("- resolved (cuda)   " << n_ambiguity_free_tracks_cuda
0570                                      << " tracks");
0571   TRACCC_INFO("- fitted (cpu)   " << n_fitted_tracks << " tracks");
0572   TRACCC_INFO("- fitted (cuda)  " << n_fitted_tracks_cuda << " tracks");
0573   TRACCC_INFO("==>Elapsed times... " << elapsedTimes);
0574 
0575   return 0;
0576 }
0577 
0578 // The main routine
0579 //
0580 int main(int argc, char* argv[]) {
0581   std::unique_ptr<const traccc::Logger> logger =
0582       traccc::getDefaultLogger("CudaSeqExample", traccc::Logging::Level::INFO);
0583 
0584   // Program options.
0585   traccc::opts::detector detector_opts;
0586   traccc::opts::magnetic_field bfield_opts;
0587   traccc::opts::input_data input_opts;
0588   traccc::opts::clusterization clusterization_opts;
0589   traccc::opts::track_seeding seeding_opts;
0590   traccc::opts::track_gbts_seeding seeding_gbts_opts;
0591   traccc::opts::track_finding finding_opts;
0592   traccc::opts::track_propagation propagation_opts;
0593   traccc::opts::track_resolution resolution_opts;
0594   traccc::opts::track_fitting fitting_opts;
0595   traccc::opts::performance performance_opts;
0596   traccc::opts::accelerator accelerator_opts;
0597   traccc::opts::program_options program_opts{
0598       "Full Tracking Chain Using CUDA",
0599       {detector_opts, bfield_opts, input_opts, clusterization_opts,
0600        seeding_opts, seeding_gbts_opts, finding_opts, propagation_opts,
0601        resolution_opts, performance_opts, fitting_opts, accelerator_opts},
0602       argc,
0603       argv,
0604       logger->cloneWithSuffix("Options")};
0605 
0606   // Run the application.
0607   return seq_run(detector_opts, bfield_opts, input_opts, clusterization_opts,
0608                  seeding_opts, seeding_gbts_opts, finding_opts,
0609                  propagation_opts, resolution_opts, fitting_opts,
0610                  performance_opts, accelerator_opts, logger->clone(),
0611                  seeding_gbts_opts.useGBTS);
0612 }