Back to home page

Project CMSSW displayed by LXR

 
 

    


File indexing completed on 2025-01-07 03:06:28

0001 #include "DataFormats/Phase2TrackerDigi/interface/Phase2ITQCore.h"
0002 #include <cmath>
0003 #include <vector>
0004 #include <iostream>
0005 
0006 //4x4 region of hits in sensor coordinates
0007 Phase2ITQCore::Phase2ITQCore(int rocid,
0008                              int ccol_in,
0009                              int qcrow_in,
0010                              bool isneighbour_in,
0011                              bool islast_in,
0012                              const std::vector<int>& adcs_in,
0013                              const std::vector<int>& hits_in) {
0014   rocid_ = rocid;
0015   ccol_ = ccol_in;
0016   qcrow_ = qcrow_in;
0017   isneighbour_ = isneighbour_in;
0018   islast_ = islast_in;
0019   adcs_ = adcs_in;
0020   hits_ = hits_in;
0021 }
0022 
0023 //Takes a hitmap in sensor coordinates in 4x4 and converts it to readout chip coordinates with 2x8
0024 std::vector<bool> Phase2ITQCore::toRocCoordinates(std::vector<bool>& hitmap) {
0025   std::vector<bool> ROC_hitmap(16, false);
0026 
0027   for (size_t i = 0; i < hitmap.size(); i++) {
0028     int row = i / 4;
0029     int col = i % 4;
0030     int new_row;
0031     int new_col;
0032 
0033     if (row % 2 == 0) {
0034       new_row = row / 2;
0035       new_col = 2 * col;
0036     } else {
0037       new_row = row / 2;
0038       new_col = 2 * col + 1;
0039     }
0040 
0041     int new_index = 8 * new_row + new_col;
0042     ROC_hitmap[new_index] = hitmap[i];
0043   }
0044 
0045   return ROC_hitmap;
0046 }
0047 
0048 //Returns the hitmap for the Phase2ITQCore in 4x4 sensor coordinates
0049 std::vector<bool> Phase2ITQCore::getHitmap() {
0050   std::vector<bool> hitmap = {};
0051 
0052   hitmap.reserve(hits_.size());
0053   for (auto hit : hits_) {
0054     hitmap.push_back(hit > 0);
0055   }
0056 
0057   return (toRocCoordinates(hitmap));
0058 }
0059 
0060 std::vector<int> Phase2ITQCore::getADCs() {
0061   std::vector<int> adcmap = {};
0062 
0063   adcmap.reserve(adcs_.size());
0064   for (auto adc : adcs_) {
0065     adcmap.push_back(adc);
0066   }
0067 
0068   return adcmap;
0069 }
0070 
0071 //Converts an integer into a binary, and formats it with the given length
0072 std::vector<bool> Phase2ITQCore::intToBinary(int num, int length) {
0073   std::vector<bool> bi_num(length, false);
0074 
0075   for (int i = 0; i < length; ++i) {
0076     // Extract the (length - 1 - i)th bit from num
0077     bi_num[i] = (num >> (length - 1 - i)) & 1;
0078   }
0079 
0080   return bi_num;
0081 }
0082 
0083 //Takes a hitmap and returns true if it contains any hits
0084 bool Phase2ITQCore::containsHit(std::vector<bool>& hitmap) {
0085   bool foundHit = false;
0086   for (size_t i = 0; i < hitmap.size(); i++) {
0087     if (hitmap[i]) {
0088       foundHit = true;
0089       break;
0090     }
0091   }
0092 
0093   return foundHit;
0094 }
0095 
0096 //Returns the Huffman encoded hitmap, created iteratively within this function
0097 std::vector<bool> Phase2ITQCore::getHitmapCode(std::vector<bool> hitmap) {
0098   std::vector<bool> code = {};
0099   // If hitmap is a single bit, there is no need to further split the bits
0100   if (hitmap.size() == 1) {
0101     return code;
0102   }
0103 
0104   std::vector<bool> left_hitmap = std::vector<bool>(hitmap.begin(), hitmap.begin() + hitmap.size() / 2);
0105   std::vector<bool> right_hitmap = std::vector<bool>(hitmap.begin() + hitmap.size() / 2, hitmap.end());
0106 
0107   bool hit_left = containsHit(left_hitmap);
0108   bool hit_right = containsHit(right_hitmap);
0109 
0110   if (hit_left && hit_right) {
0111     code.push_back(true);
0112     code.push_back(true);
0113 
0114     std::vector<bool> left_code = getHitmapCode(left_hitmap);
0115     std::vector<bool> right_code = getHitmapCode(right_hitmap);
0116 
0117     code.insert(code.end(), left_code.begin(), left_code.end());
0118     code.insert(code.end(), right_code.begin(), right_code.end());
0119 
0120   } else if (hit_right) {
0121     //Huffman encoding compresses 01 into 0
0122     code.push_back(false);
0123 
0124     std::vector<bool> right_code = getHitmapCode(right_hitmap);
0125     code.insert(code.end(), right_code.begin(), right_code.end());
0126 
0127   } else if (hit_left) {
0128     code.push_back(true);
0129     code.push_back(false);
0130 
0131     std::vector<bool> left_code = getHitmapCode(left_hitmap);
0132     code.insert(code.end(), left_code.begin(), left_code.end());
0133   }
0134 
0135   return code;
0136 }
0137 
0138 //Returns the bit code associated with the Phase2ITQCore
0139 std::vector<bool> Phase2ITQCore::encodeQCore(bool is_new_col) {
0140   std::vector<bool> code = {};
0141 
0142   if (is_new_col) {
0143     std::vector<bool> col_code = intToBinary(ccol_, 6);
0144     code.insert(code.end(), col_code.begin(), col_code.end());
0145   }
0146 
0147   code.push_back(islast_);
0148   code.push_back(isneighbour_);
0149 
0150   if (!isneighbour_) {
0151     std::vector<bool> row_code = intToBinary(qcrow_, 8);
0152     code.insert(code.end(), row_code.begin(), row_code.end());
0153   }
0154 
0155   std::vector<bool> hitmap_code = getHitmapCode(getHitmap());
0156   code.insert(code.end(), hitmap_code.begin(), hitmap_code.end());
0157 
0158   for (auto adc : adcs_) {
0159     std::vector<bool> adc_code = intToBinary(adc, 4);
0160     code.insert(code.end(), adc_code.begin(), adc_code.end());
0161   }
0162 
0163   return code;
0164 }