Line Code
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190
#include "Geometry/MTDGeometryBuilder/interface/MTDGeomBuilderFromGeometricTimingDet.h"
#include "Geometry/MTDGeometryBuilder/interface/MTDGeometry.h"
#include "Geometry/CommonDetUnit/interface/GeomDet.h"
#include "Geometry/MTDGeometryBuilder/interface/MTDGeomDetType.h"
#include "Geometry/MTDGeometryBuilder/interface/MTDGeomDetUnit.h"
#include "Geometry/MTDGeometryBuilder/interface/MTDPixelTopologyBuilder.h"
#include "DataFormats/DetId/interface/DetId.h"
#include "DataFormats/ForwardDetId/interface/MTDDetId.h"
#include "CondFormats/GeometryObjects/interface/PMTDParameters.h"
#include "DataFormats/GeometrySurface/interface/MediumProperties.h"
#include "FWCore/MessageLogger/interface/MessageLogger.h"
#include "FWCore/Utilities/interface/Exception.h"

#include <cfloat>
#include <cassert>
using std::string;
using std::vector;

namespace {
  void verifyDUinTG(MTDGeometry const& tg) {
    int off = 0;
    int end = 0;
    for (int i = 1; i != 2; i++) {
      auto det = i - 1;
      off = tg.offsetDU(det);
      end = tg.endsetDU(det);
      assert(end >= off);  // allow empty subdetectors. Needed for upgrade
      for (int j = off; j != end; ++j) {
        assert(tg.detUnits()[j]->geographicalId().subdetId() == i);
        assert(tg.detUnits()[j]->index() == j);
      }
    }
  }
}  // namespace

MTDGeometry* MTDGeomBuilderFromGeometricTimingDet::build(const GeometricTimingDet* gd, const PMTDParameters& ptp) {
  theMTDDetTypeMap.clear();

  MTDGeometry* tracker = new MTDGeometry(gd);
  std::vector<const GeometricTimingDet*> comp;
  gd->deepComponents(comp);

  //define a vector which associate to the detid subdetector index -1 (from 0 to 5) the GeometridDet enumerator to be able to know which type of subdetector it is

  std::vector<GeometricTimingDet::GTDEnumType> gdsubdetmap(
      2, GeometricTimingDet::unknown);  // hardcoded "2" should not be a surprise...
  GeometricTimingDet::ConstGeometricTimingDetContainer subdetgd = gd->components();

  LogDebug("SubDetectorGeometricTimingDetType") << "MTD GeometricTimingDet enumerator values of the subdetectors";
  for (unsigned int i = 0; i < subdetgd.size(); ++i) {
    MTDDetId mtdid(subdetgd[i]->geographicalId());
    assert(mtdid.mtdSubDetector() > 0 && mtdid.mtdSubDetector() < 3);
    gdsubdetmap[mtdid.mtdSubDetector() - 1] = subdetgd[i]->type();
    LogTrace("SubDetectorGeometricTimingDetType") << "MTD subdet " << i << " type " << subdetgd[i]->type() << " detid "
                                                  << std::hex << subdetgd[i]->geographicalId().rawId() << std::dec
                                                  << " subdetid " << subdetgd[i]->geographicalId().subdetId();
  }

  std::vector<const GeometricTimingDet*> dets[2];
  std::vector<const GeometricTimingDet*>& btl = dets[0];
  btl.reserve(comp.size());
  std::vector<const GeometricTimingDet*>& etl = dets[1];
  etl.reserve(comp.size());

  for (auto& i : comp) {
    MTDDetId mtdid(i->geographicalId());
    dets[mtdid.mtdSubDetector() - 1].emplace_back(i);
  }

  //loop on all the six elements of dets and firstly check if they are from pixel-like detector and call buildPixel, then loop again and check if they are strip and call buildSilicon. "unknown" can be filled either way but the vector of GeometricTimingDet must be empty !!
  // this order is VERY IMPORTANT!!!!! For the moment I (AndreaV) understand that some pieces of code rely on pixel-like being before strip-like

  // now building the Pixel-like subdetectors
  for (unsigned int i = 0; i < 2; ++i) {
    if (gdsubdetmap[i] == GeometricTimingDet::BTL)
      buildPixel(dets[i], tracker, GeomDetEnumerators::SubDetector::TimingBarrel, ptp);
    if (gdsubdetmap[i] == GeometricTimingDet::ETL)
      buildPixel(dets[i], tracker, GeomDetEnumerators::SubDetector::TimingEndcap, ptp);
  }

  buildGeomDet(tracker);  //"GeomDet"

  verifyDUinTG(*tracker);

  return tracker;
}

void MTDGeomBuilderFromGeometricTimingDet::buildPixel(
    std::vector<const GeometricTimingDet*> const& gdv,
    MTDGeometry* tracker,
    GeomDetType::SubDetector det,
    const PMTDParameters& ptp)  // in y direction, cols. BIG_PIX_PER_ROC_Y = 0 for SLHC
{
  LogDebug("BuildingGeomDetUnits") << " MTD Pixel type. Size of vector: " << gdv.size()
                                   << " GeomDetType subdetector: " << det
                                   << " logical subdetector: " << GeomDetEnumerators::subDetGeom[det]
                                   << " big pix per ROC x: " << 0 << " y: " << 0 << " is upgrade: " << true;

  // this is a hack while we put things into the DDD
  int ROCrows(0), ROCcols(0), ROCSx(0), ROCSy(0);
  int GAPxInterpad(0), GAPxBorder(0), GAPyInterpad(0), GAPyBorder(0);
  switch (det) {
    case GeomDetType::SubDetector::TimingBarrel:
      GAPxInterpad = ptp.vitems_[0].vpars_[4];  // Value given in microns
      GAPxBorder = ptp.vitems_[0].vpars_[5];    // Value given in microns
      GAPyInterpad = ptp.vitems_[0].vpars_[6];  // Value given in microns
      GAPyBorder = ptp.vitems_[0].vpars_[7];    // Value given in microns
      ROCrows = ptp.vitems_[0].vpars_[8];
      ROCcols = ptp.vitems_[0].vpars_[9];
      ROCSx = ptp.vitems_[0].vpars_[10];
      ROCSy = ptp.vitems_[0].vpars_[11];
      break;
    case GeomDetType::SubDetector::TimingEndcap:
      GAPxInterpad = ptp.vitems_[1].vpars_[4];
      GAPxBorder = ptp.vitems_[1].vpars_[5];
      GAPyInterpad = ptp.vitems_[1].vpars_[6];
      GAPyBorder = ptp.vitems_[1].vpars_[7];
      ROCrows = ptp.vitems_[1].vpars_[8];
      ROCcols = ptp.vitems_[1].vpars_[9];
      ROCSx = ptp.vitems_[1].vpars_[10];
      ROCSy = ptp.vitems_[1].vpars_[11];
      break;
      break;
    default:
      throw cms::Exception("UnknownDet") << "MTDGeomBuilderFromGeometricTimingDet got a weird detector: " << det;
  }

  switch (det) {
    case GeomDetEnumerators::TimingBarrel:
      tracker->setOffsetDU(0);
      break;
    case GeomDetEnumerators::TimingEndcap:
      tracker->setOffsetDU(1);
      break;
    default:
      throw cms::Exception("MTDGeomBuilderFromGeometricTimingDet") << det << " is not a timing detector!";
  }

  for (auto i : gdv) {
    std::string const& detName = i->name();
    if (theMTDDetTypeMap.find(detName) == theMTDDetTypeMap.end()) {
      std::unique_ptr<const Bounds> bounds(i->bounds());

      PixelTopology* t = MTDPixelTopologyBuilder().build(
          &*bounds, ROCrows, ROCcols, ROCSx, ROCSy, GAPxInterpad, GAPxBorder, GAPyInterpad, GAPyBorder);

      theMTDDetTypeMap[detName] = new MTDGeomDetType(t, detName, det);
      tracker->addType(theMTDDetTypeMap[detName]);
    }

    PlaneBuilderFromGeometricTimingDet::ResultType plane = buildPlaneWithMaterial(i);
    GeomDetUnit* temp = new MTDGeomDetUnit(&(*plane), theMTDDetTypeMap[detName], i->geographicalID());

    tracker->addDetUnit(temp);
    tracker->addDetUnitId(i->geographicalID());
  }
  switch (det) {
    case GeomDetEnumerators::TimingBarrel:
      tracker->setEndsetDU(0);
      break;
    case GeomDetEnumerators::TimingEndcap:
      tracker->setEndsetDU(1);
      break;
    default:
      throw cms::Exception("MTDGeomBuilderFromGeometricTimingDet") << det << " is not a timing detector!";
  }
}

void MTDGeomBuilderFromGeometricTimingDet::buildGeomDet(MTDGeometry* tracker) {
  auto const& gdu = tracker->detUnits();
  auto const& gduId = tracker->detUnitIds();

  for (u_int32_t i = 0; i < gdu.size(); i++) {
    tracker->addDet(gdu[i]);
    tracker->addDetId(gduId[i]);
    string gduTypeName = gdu[i]->type().name();
  }
}

PlaneBuilderFromGeometricTimingDet::ResultType MTDGeomBuilderFromGeometricTimingDet::buildPlaneWithMaterial(
    const GeometricTimingDet* gd, double scale) const {
  PlaneBuilderFromGeometricTimingDet planeBuilder;
  PlaneBuilderFromGeometricTimingDet::ResultType plane = planeBuilder.plane(gd);
  //
  // set medium properties (if defined)
  //
  plane->setMediumProperties(MediumProperties(gd->radLength() * scale, gd->xi() * scale));

  return plane;
}