File indexing completed on 2025-09-17 08:53:42
0001
0002
0003
0004
0005
0006
0007 #pragma once
0008
0009 #include "corecel/Macros.hh"
0010 #include "corecel/Types.hh"
0011 #include "corecel/math/Algorithms.hh"
0012 #include "celeritas/track/CoreStateCounters.hh"
0013
0014 #include "OpticalUtils.hh"
0015 #include "../CherenkovGenerator.hh"
0016 #include "../CoreTrackView.hh"
0017 #include "../OffloadData.hh"
0018
0019 namespace celeritas
0020 {
0021 namespace detail
0022 {
0023
0024
0025
0026
0027
0028
0029 struct CherenkovGeneratorExecutor
0030 {
0031
0032
0033 RefPtr<CoreStateData, MemSpace::native> state;
0034 NativeCRef<celeritas::optical::MaterialParamsData> const material;
0035 NativeCRef<celeritas::optical::CherenkovData> const cherenkov;
0036 NativeRef<OffloadStateData> const offload_state;
0037 RefPtr<celeritas::optical::CoreStateData, MemSpace::native> optical_state;
0038 OpticalOffloadCounters<> size;
0039 CoreStateCounters counters;
0040
0041
0042
0043
0044 inline CELER_FUNCTION void operator()(CoreTrackView const& track) const;
0045 };
0046
0047
0048
0049
0050
0051
0052
0053 CELER_FUNCTION void
0054 CherenkovGeneratorExecutor::operator()(CoreTrackView const& track) const
0055 {
0056 CELER_EXPECT(state);
0057 CELER_EXPECT(cherenkov);
0058 CELER_EXPECT(material);
0059 CELER_EXPECT(offload_state);
0060 CELER_EXPECT(optical_state);
0061 CELER_EXPECT(size.cherenkov <= offload_state.cherenkov.size());
0062
0063 using DistId = ItemId<celeritas::optical::GeneratorDistributionData>;
0064 using InitId = ItemId<celeritas::optical::TrackInitializer>;
0065
0066
0067
0068
0069 auto offsets = offload_state.offsets[ItemRange<size_type>(
0070 ItemId<size_type>(0), ItemId<size_type>(size.cherenkov))];
0071
0072
0073 size_type total_work = offsets.back();
0074
0075
0076 size_type local_work = LocalWorkCalculator<size_type>{
0077 total_work, state->size()}(track.thread_id().get());
0078
0079 auto rng = track.rng();
0080
0081 for (auto i : range(local_work))
0082 {
0083
0084 size_type idx = i * state->size() + track.thread_id().get();
0085
0086
0087 size_type dist_idx = find_distribution_index(offsets, idx);
0088 CELER_ASSERT(dist_idx < size.cherenkov);
0089 auto const& dist = offload_state.cherenkov[DistId(dist_idx)];
0090 CELER_ASSERT(dist);
0091
0092
0093 optical::MaterialView opt_mat{material, dist.material};
0094 celeritas::optical::CherenkovGenerator generate(opt_mat, cherenkov, dist);
0095 size_type init_idx = counters.num_initializers + idx;
0096 CELER_ASSERT(init_idx < optical_state->init.initializers.size());
0097 optical_state->init.initializers[InitId(init_idx)] = generate(rng);
0098 }
0099 }
0100
0101
0102 }
0103 }