CMS 3D CMS Logo

SiPixelRecHitSoAFromLegacy.cc
Go to the documentation of this file.
1 #include <cuda_runtime.h>
2 
28 
29 #include "gpuPixelRecHits.h"
30 
31 template <typename TrackerTraits>
33 public:
34  explicit SiPixelRecHitSoAFromLegacyT(const edm::ParameterSet& iConfig);
35  ~SiPixelRecHitSoAFromLegacyT() override = default;
36 
37  static void fillDescriptions(edm::ConfigurationDescriptions& descriptions);
38 
39  using HitModuleStart = std::array<uint32_t, TrackerTraits::numberOfModules + 1>;
42 
43 private:
44  void produce(edm::StreamID streamID, edm::Event& iEvent, const edm::EventSetup& iSetup) const override;
45 
52  const bool convert2Legacy_;
53 };
54 
55 template <typename TrackerTraits>
57  : geomToken_(esConsumes()),
58  cpeToken_(esConsumes(edm::ESInputTag("", iConfig.getParameter<std::string>("CPE")))),
59  bsGetToken_{consumes<reco::BeamSpot>(iConfig.getParameter<edm::InputTag>("beamSpot"))},
60  clusterToken_{consumes<SiPixelClusterCollectionNew>(iConfig.getParameter<edm::InputTag>("src"))},
61  tokenHit_{produces<HitsOnHost>()},
62  tokenModuleStart_{produces<HMSstorage>()},
63  convert2Legacy_(iConfig.getParameter<bool>("convertToLegacy")) {
64  if (convert2Legacy_)
65  produces<SiPixelRecHitCollectionNew>();
66 }
67 
68 template <typename TrackerTraits>
71 
72  desc.add<edm::InputTag>("beamSpot", edm::InputTag("offlineBeamSpot"));
73  desc.add<edm::InputTag>("src", edm::InputTag("siPixelClustersPreSplitting"));
74  std::string cpeName = "PixelCPEFast";
75  cpeName += TrackerTraits::nameModifier;
76  desc.add<std::string>("CPE", cpeName);
77  desc.add<bool>("convertToLegacy", false);
78 
79  descriptions.addWithDefaultLabel(desc);
80 }
81 
82 template <typename TrackerTraits>
85  const edm::EventSetup& es) const {
86  const TrackerGeometry* geom_ = &es.getData(geomToken_);
87  PixelCPEFast<TrackerTraits> const* fcpe = dynamic_cast<const PixelCPEFast<TrackerTraits>*>(&es.getData(cpeToken_));
88  if (not fcpe) {
89  throw cms::Exception("Configuration") << "SiPixelRecHitSoAFromLegacy can only use a CPE of type PixelCPEFast";
90  }
91  auto const& cpeView = fcpe->getCPUProduct();
92 
93  const reco::BeamSpot& bs = iEvent.get(bsGetToken_);
94 
95  BeamSpotPOD bsHost;
96  bsHost.x = bs.x0();
97  bsHost.y = bs.y0();
98  bsHost.z = bs.z0();
99 
101  iEvent.getByToken(clusterToken_, hclusters);
102  auto const& input = *hclusters;
103 
104  constexpr int nModules = TrackerTraits::numberOfModules;
105  constexpr int startBPIX2 = pixelTopology::layerStart<TrackerTraits>(1);
106 
107  // allocate a buffer for the indices of the clusters
108  auto hmsp = std::make_unique<uint32_t[]>(nModules + 1);
109  auto hitsModuleStart = hmsp.get();
110  // wrap the buffer in a HostProduct
111  auto hms = std::make_unique<HMSstorage>(std::move(hmsp));
112  // move the HostProduct to the Event, without reallocating the buffer or affecting hitsModuleStart
113  iEvent.put(tokenModuleStart_, std::move(hms));
114 
115  // legacy output
116  auto legacyOutput = std::make_unique<SiPixelRecHitCollectionNew>();
117 
118  std::vector<edm::Ref<edmNew::DetSetVector<SiPixelCluster>, SiPixelCluster>> clusterRef;
119 
120  constexpr uint32_t maxHitsInModule = TrackerTraits::maxNumClustersPerModules;
121 
123 
124  memset(clusters_h.view().clusInModule(), 0, (nModules + 1) * sizeof(uint32_t)); // needed??
125  memset(clusters_h.view().moduleStart(), 0, (nModules + 1) * sizeof(uint32_t));
126  memset(clusters_h.view().moduleId(), 0, (nModules + 1) * sizeof(uint32_t));
127  memset(clusters_h.view().clusModuleStart(), 0, (nModules + 1) * sizeof(uint32_t));
128 
129  assert(0 == clusters_h.view()[nModules].clusInModule());
130  clusters_h.view()[1].moduleStart() = 0;
131 
132  // fill cluster arrays
133  int numberOfClusters = 0;
134  for (auto const& dsv : input) {
135  unsigned int detid = dsv.detId();
136  DetId detIdObject(detid);
137  const GeomDetUnit* genericDet = geom_->idToDetUnit(detIdObject);
138  auto gind = genericDet->index();
139  assert(gind < nModules);
140  auto const nclus = dsv.size();
141  clusters_h.view()[gind].clusInModule() = nclus;
142  numberOfClusters += nclus;
143  }
144  clusters_h.view()[0].clusModuleStart() = 0;
145 
146  for (int i = 1; i < nModules + 1; ++i) {
147  clusters_h.view()[i].clusModuleStart() =
148  clusters_h.view()[i - 1].clusModuleStart() + clusters_h.view()[i - 1].clusInModule();
149  }
150 
151  assert((uint32_t)numberOfClusters == clusters_h.view()[nModules].clusModuleStart());
152  // output SoA
153  // element 96 is the start of BPIX2 (i.e. the number of clusters in BPIX1)
155  numberOfClusters, clusters_h.view()[startBPIX2].clusModuleStart(), &cpeView, clusters_h.view().clusModuleStart());
156 
157  if (0 == numberOfClusters) {
158  iEvent.emplace(tokenHit_, std::move(output));
159  if (convert2Legacy_)
160  iEvent.put(std::move(legacyOutput));
161  return;
162  }
163 
164  if (convert2Legacy_)
165  legacyOutput->reserve(nModules, numberOfClusters);
166 
167  int numberOfDetUnits = 0;
168  int numberOfHits = 0;
169  for (auto const& dsv : input) {
170  numberOfDetUnits++;
171  unsigned int detid = dsv.detId();
172  DetId detIdObject(detid);
173  const GeomDetUnit* genericDet = geom_->idToDetUnit(detIdObject);
174  auto const gind = genericDet->index();
175  assert(gind < nModules);
176  const PixelGeomDetUnit* pixDet = dynamic_cast<const PixelGeomDetUnit*>(genericDet);
177  assert(pixDet);
178  auto const nclus = dsv.size();
179 
180  assert(clusters_h.view()[gind].clusInModule() == nclus);
181  if (0 == nclus)
182  continue; // is this really possible?
183 
184  auto const fc = clusters_h.view()[gind].clusModuleStart();
185  auto const lc = clusters_h.view()[gind + 1].clusModuleStart();
186  assert(lc > fc);
187  LogDebug("SiPixelRecHitSoAFromLegacy") << "in det " << gind << ": conv " << nclus << " hits from " << dsv.size()
188  << " legacy clusters" << ' ' << fc << ',' << lc;
189  assert((lc - fc) == nclus);
190  if (nclus > maxHitsInModule)
191  printf(
192  "WARNING: too many clusters %d in Module %d. Only first %d Hits converted\n", nclus, gind, maxHitsInModule);
193 
194  // count digis
195  uint32_t ndigi = 0;
196  for (auto const& clust : dsv) {
197  assert(clust.size() > 0);
198  ndigi += clust.size();
199  }
200 
202 
203  clusterRef.clear();
204  clusters_h.view()[0].moduleId() = gind;
205 
206  uint32_t ic = 0;
207  ndigi = 0;
208  //filling digis
209  for (auto const& clust : dsv) {
210  assert(clust.size() > 0);
211  for (int i = 0, nd = clust.size(); i < nd; ++i) {
212  auto px = clust.pixel(i);
213  digis_h.view()[ndigi].xx() = px.x;
214  digis_h.view()[ndigi].yy() = px.y;
215  digis_h.view()[ndigi].adc() = px.adc;
216  digis_h.view()[ndigi].moduleId() = gind;
217  digis_h.view()[ndigi].clus() = ic;
218  ++ndigi;
219  }
220 
221  if (convert2Legacy_)
222  clusterRef.emplace_back(edmNew::makeRefTo(hclusters, &clust));
223  ic++;
224  }
225  assert(nclus == ic);
226 
227  numberOfHits += nclus;
228  // filled creates view
229  assert(digis_h.view()[0].adc() != 0);
230  // we run on blockId.x==0
231 
232  gpuPixelRecHits::getHits(&cpeView, &bsHost, digis_h.view(), ndigi, clusters_h.view(), output.view());
233  for (auto h = fc; h < lc; ++h)
234  if (h - fc < maxHitsInModule)
235  assert(gind == output.view()[h].detectorIndex());
236  else
237  assert(gpuClustering::invalidModuleId == output.view()[h].detectorIndex());
238 
239  if (convert2Legacy_) {
240  SiPixelRecHitCollectionNew::FastFiller recHitsOnDetUnit(*legacyOutput, detid);
241  for (auto h = fc; h < lc; ++h) {
242  auto ih = h - fc;
243 
244  if (ih >= maxHitsInModule)
245  break;
246 
247  assert(ih < clusterRef.size());
248  LocalPoint lp(output.view()[h].xLocal(), output.view()[h].yLocal());
249  LocalError le(output.view()[h].xerrLocal(), 0, output.view()[h].yerrLocal());
250 
252  SiPixelRecHit hit(lp, le, rqw, *genericDet, clusterRef[ih]);
253  recHitsOnDetUnit.push_back(hit);
254  }
255  }
256  }
257 
258  assert(numberOfHits == numberOfClusters);
259 
260  // fill data structure to support CA
261  constexpr auto nLayers = TrackerTraits::numberOfLayers;
262  for (auto i = 0U; i < nLayers + 1; ++i) {
263  output.view().hitsLayerStart()[i] = clusters_h.view()[cpeView.layerGeometry().layerStart[i]].clusModuleStart();
264  LogDebug("SiPixelRecHitSoAFromLegacy")
265  << "Layer n." << i << " - starting at module: " << cpeView.layerGeometry().layerStart[i]
266  << " - starts ad cluster: " << output->hitsLayerStart()[i] << "\n";
267  }
268 
269  cms::cuda::fillManyFromVector(&(output.view().phiBinner()),
270  nLayers,
271  output.view().iphi(),
272  output.view().hitsLayerStart().data(),
273  output.view().nHits(),
274  256,
275  output.view().phiBinnerStorage());
276 
277  LogDebug("SiPixelRecHitSoAFromLegacy") << "created HitSoa for " << numberOfClusters << " clusters in "
278  << numberOfDetUnits << " Dets"
279  << "\n";
280 
281  // copy pointer to data (SoA view) to allocated buffer
282  memcpy(hitsModuleStart, clusters_h.view().clusModuleStart(), nModules * sizeof(uint32_t));
283 
284  iEvent.emplace(tokenHit_, std::move(output));
285  if (convert2Legacy_)
286  iEvent.put(std::move(legacyOutput));
287 }
288 
291 
294 
edm::Ref< typename HandleT::element_type, typename HandleT::element_type::value_type::value_type > makeRefTo(const HandleT &iHandle, typename HandleT::element_type::value_type::const_iterator itIter)
void addWithDefaultLabel(ParameterSetDescription const &psetDescription)
void push_back(data_type const &d)
ESGetTokenH3DDVariant esConsumes(std::string const &Record, edm::ConsumesCollector &)
Definition: DeDxTools.cc:283
T getParameter(std::string const &) const
Definition: ParameterSet.h:303
std::array< uint32_t, TrackerTraits::numberOfModules+1 > HitModuleStart
~SiPixelRecHitSoAFromLegacyT() override=default
T const & getData(const ESGetToken< T, R > &iToken) const noexcept(false)
Definition: EventSetup.h:119
const TrackerGeomDet * idToDetUnit(DetId) const override
Return the pointer to the GeomDetUnit corresponding to a given DetId.
constexpr uint32_t numberOfLayers
int index() const
Definition: GeomDet.h:83
const edm::EDPutTokenT< HMSstorage > tokenModuleStart_
assert(be >=bs)
constexpr uint16_t numberOfModules
static std::string const input
Definition: EdmProvDump.cc:50
const edm::EDPutTokenT< HitsOnHost > tokenHit_
constexpr uint32_t maxNumClustersPerModules
const edm::ESGetToken< TrackerGeometry, TrackerDigiGeometryRecord > geomToken_
int iEvent
Definition: GenABIO.cc:224
constexpr int startBPIX2
void produce(edm::StreamID streamID, edm::Event &iEvent, const edm::EventSetup &iSetup) const override
const edm::ESGetToken< PixelClusterParameterEstimator, TkPixelCPERecord > cpeToken_
#define DEFINE_FWK_MODULE(type)
Definition: MakerMacros.h:16
constexpr uint16_t invalidModuleId
const edm::EDGetTokenT< reco::BeamSpot > bsGetToken_
Definition: DetId.h:17
Pixel cluster – collection of neighboring pixels above threshold.
HLT enums.
SiPixelRecHitSoAFromLegacyT(const edm::ParameterSet &iConfig)
static void fillDescriptions(edm::ConfigurationDescriptions &descriptions)
The Signals That Services Can Subscribe To This is based on ActivityRegistry h
Helper function to determine trigger accepts.
Definition: Activities.doc:4
def move(src, dest)
Definition: eostools.py:511
const edm::EDGetTokenT< SiPixelClusterCollectionNew > clusterToken_
Our base class.
Definition: SiPixelRecHit.h:23
#define LogDebug(id)