hps-java/src/main/java/org/lcsim/hps/evio
diff -u -r1.2 -r1.3
--- TestRunReconToEvio.java 29 Mar 2012 04:14:14 -0000 1.2
+++ TestRunReconToEvio.java 1 Apr 2012 21:20:56 -0000 1.3
@@ -37,227 +37,227 @@
* @author Jeremy McCormick <[log in to unmask]>
*/
public class TestRunReconToEvio extends Driver {
-
- EventWriter writer;
-
- String rawCalorimeterHitCollectionName = "EcalDigitizedHits";
- String svtCollectionName = "SVTData";
- String evioOutputFile = "MCRawData.evio";
-
- EventBuilder builder = null;
- private int eventsWritten = 0;
-
- public TestRunReconToEvio()
- {}
-
- public void setEvioOutputFile(String evioOutputFile) {
- this.evioOutputFile = evioOutputFile;
- }
-
- public void setSVTDataCollectionName(String svtCollectionName) {
- this.svtCollectionName = svtCollectionName;
- }
-
- public void setRawCalorimeterHitCollectionName(String rawCalorimeterHitCollectionName) {
- this.rawCalorimeterHitCollectionName = rawCalorimeterHitCollectionName;
- }
-
- protected void startOfData() {
- try {
- writer = new EventWriter(evioOutputFile);
- }
- catch (EvioException e) {
- throw new RuntimeException(e);
- }
- }
-
- protected void endOfData() {
- System.out.println(this.getClass().getSimpleName() + " - wrote " + eventsWritten + " EVIO events in job.");
- try {
- writer.close();
- } catch (EvioException e) {
- throw new RuntimeException(e);
- } catch (IOException e) {
- throw new RuntimeException(e);
- }
- }
-
- protected void process(EventHeader event) {
-
- // Make a new EVIO event.
- builder = new EventBuilder(0, DataType.BANK, event.getEventNumber());
-
- // Write SVTData.
- writeSVTData(event);
-
- // Write RawCalorimeterHit collection.
- writeRawCalorimeterHits(event);
-
- // Write this EVIO event.
- writeEvioEvent();
- }
+
+ EventWriter writer;
+ String rawCalorimeterHitCollectionName = "EcalDigitizedHits";
+ String svtCollectionName = "SVTData";
+ String evioOutputFile = "MCRawData.evio";
+ EventBuilder builder = null;
+ private int eventsWritten = 0;
+
+ public TestRunReconToEvio() {
+ }
+
+ public void setEvioOutputFile(String evioOutputFile) {
+ this.evioOutputFile = evioOutputFile;
+ }
+
+ public void setSVTDataCollectionName(String svtCollectionName) {
+ this.svtCollectionName = svtCollectionName;
+ }
+
+ public void setRawCalorimeterHitCollectionName(String rawCalorimeterHitCollectionName) {
+ this.rawCalorimeterHitCollectionName = rawCalorimeterHitCollectionName;
+ }
+
+ protected void startOfData() {
+ try {
+ writer = new EventWriter(evioOutputFile);
+ } catch (EvioException e) {
+ throw new RuntimeException(e);
+ }
+ }
+
+ protected void endOfData() {
+ System.out.println(this.getClass().getSimpleName() + " - wrote " + eventsWritten + " EVIO events in job.");
+ try {
+ writer.close();
+ } catch (EvioException e) {
+ throw new RuntimeException(e);
+ } catch (IOException e) {
+ throw new RuntimeException(e);
+ }
+ }
+
+ protected void process(EventHeader event) {
+
+ // Make a new EVIO event.
+ builder = new EventBuilder(0, DataType.BANK, event.getEventNumber());
+
+ // Write SVTData.
+ writeSVTData(event);
+
+ // Write RawCalorimeterHit collection.
+ writeRawCalorimeterHits(event);
+
+ // Write this EVIO event.
+ writeEvioEvent();
+ }
private void writeEvioEvent() {
builder.setAllHeaderLengths();
- try {
- writer.writeEvent(builder.getEvent());
- ++eventsWritten;
- } catch (EvioException e) {
- throw new RuntimeException(e);
- } catch (IOException e) {
- throw new RuntimeException(e);
- }
+ try {
+ writer.writeEvent(builder.getEvent());
+ ++eventsWritten;
+ } catch (EvioException e) {
+ throw new RuntimeException(e);
+ } catch (IOException e) {
+ throw new RuntimeException(e);
+ }
}
private void writeRawCalorimeterHits(EventHeader event) {
- List<RawCalorimeterHit> rawCalorimeterHits = event.get(RawCalorimeterHit.class, rawCalorimeterHitCollectionName);
- LCMetaData meta = event.getMetaData(rawCalorimeterHits);
- writeRawCalorimeterHits(meta, rawCalorimeterHits, builder);
+ List<RawCalorimeterHit> rawCalorimeterHits = event.get(RawCalorimeterHit.class, rawCalorimeterHitCollectionName);
+ LCMetaData meta = event.getMetaData(rawCalorimeterHits);
+ writeRawCalorimeterHits(meta, rawCalorimeterHits, builder);
}
private void writeSVTData(EventHeader event) {
List<List<HPSSVTData>> svtDataList = event.get(HPSSVTData.class);
- if (svtDataList != null) {
- if (svtDataList.size() > 0) {
- if (svtDataList.get(0) != null) {
- this.writeSVTData(svtDataList.get(0));
- }
- }
- }
- }
-
- private void writeSVTData(List<HPSSVTData> data) {
- if (data == null) {
- throw new RuntimeException("The list points to null.");
- }
-
- int nsamples = data.size();
- int evioIntData[] = new int[nsamples*4];
-
- int i = 0;
- for (HPSSVTData sample : data) {
- int[] sampleData = sample.getData();
- //System.out.println(Integer.toHexString(sampleData[0]) + ":" + Integer.toHexString(sampleData[1])+ ":" + Integer.toHexString(sampleData[2])+ ":" + Integer.toHexString(sampleData[3]));
- evioIntData[i] = sampleData[0];
- evioIntData[i+1] = sampleData[1];
- evioIntData[i+2] = sampleData[2];
- evioIntData[i+3] = sampleData[3];
- i += 4;
- }
- EvioBank bank = new EvioBank(SVT_BANK_TAG, DataType.UINT32, SVT_BANK_NUMBER);
- try {
- bank.appendIntData(evioIntData);
- } catch (EvioException e) {
- throw new RuntimeException(e);
- }
- bank.setAllHeaderLengths();
- try {
- builder.addChild(builder.getEvent(), bank);
- } catch (EvioException e) {
- throw new RuntimeException(e);
- }
- }
-
- private void writeRawCalorimeterHitCollection(List<RawCalorimeterHit> hits, LCMetaData meta, int bankTag, EventBuilder builder) {
-
- // Get the ID decoder.
- IDDecoder dec = meta.getIDDecoder();
-
- // Make a hit map.
- Map<Long,RawCalorimeterHit> hitMap = new HashMap<Long,RawCalorimeterHit>();
- for (RawCalorimeterHit hit : hits) {
- hitMap.put(hit.getCellID(), hit);
- }
-
- // Make map of slot number to hit IDs.
- Map<Integer,List<Long>> slotMap = new HashMap<Integer,List<Long>>();
- for (Long id : hitMap.keySet()) {
- dec.setID(id);
- int iy = dec.getValue("iy"); // treating as slot number
- int slot = Math.abs(iy);
- if (slotMap.get(slot) == null) {
- slotMap.put(slot, new ArrayList<Long>());
- }
- List<Long> slots = slotMap.get(slot);
- slots.add(id);
- }
-
- // Make a new bank for this crate.
- EvioBank crateBank = new EvioBank(bankTag, DataType.BANK, ECAL_BANK_NUMBER);
-
- // Loop over the slots in the map.
- for (int slot : slotMap.keySet()) {
-
- // New bank for this slot.
- EvioBank slotBank = new EvioBank(ECAL_PULSE_INTEGRAL_BANK_TAG, DataType.COMPOSITE, slot);
-
- // Create composite data for this slot and its channels.
- CompositeData.Data data = new CompositeData.Data();
- data.addUchar((byte)slot); // slot #
- data.addUint(0); // trigger #
- data.addUlong(0); // timestamp
- List<Long> hitIDs = slotMap.get(slot);
- int nhits = hitIDs.size();
- data.addN(nhits); // number of channels
- for (Long id : hitIDs) {
- dec.setID(id);
- int ix = dec.getValue("ix");
- int channel = ix + ECAL_CHANNEL_OFFSET;
- data.addUchar((byte)channel); // channel #
- data.addN(1); // number of pulses
- RawCalorimeterHit hit = hitMap.get(id);
- data.addUshort((short)hit.getTimeStamp()); // pulse time
- data.addUint((int)hit.getAmplitude()); // pulse integral
- }
-
- // Add CompositeData to bank.
- CompositeData cdata = null;
- try {
- cdata = new CompositeData(ECAL_PULSE_INTEGRAL_FORMAT, 1, data, ECAL_PULSE_INTEGRAL_BANK_TAG, slot);
- slotBank.appendCompositeData(cdata);
- }
- catch (EvioException e) {
- throw new RuntimeException(e);
- }
-
- // Add slot bank to crate bank.
- slotBank.setAllHeaderLengths();
- try {
- builder.addChild(crateBank, slotBank);
- } catch (EvioException e) {
- throw new RuntimeException(e);
- }
- }
- try {
- crateBank.setAllHeaderLengths();
- builder.addChild(builder.getEvent(), crateBank);
- } catch (EvioException e) {
- throw new RuntimeException(e);
- }
- }
-
- private void writeRawCalorimeterHits(LCMetaData meta, List<RawCalorimeterHit> rawCalorimeterHits, EventBuilder builder) {
-
- // Make two lists containing the hits from top and bottom sections, which go into separate EVIO data banks.
- IDDecoder dec = meta.getIDDecoder();
- List<RawCalorimeterHit> topHits = new ArrayList<RawCalorimeterHit>();
- List<RawCalorimeterHit> bottomHits = new ArrayList<RawCalorimeterHit>();
- for (RawCalorimeterHit hit : rawCalorimeterHits) {
- dec.setID(hit.getCellID());
- int iy = dec.getValue("iy");
- // Negative iy should be bottom section.
- if (iy < 0) {
- bottomHits.add(hit);
- }
- // Positive iy should be top section.
- else {
- topHits.add(hit);
- }
- }
-
- // Write the two collections for top and bottom hits to separate EVIO banks.
- writeRawCalorimeterHitCollection(topHits, meta, ECAL_TOP_BANK_TAG, builder);
- writeRawCalorimeterHitCollection(bottomHits, meta, ECAL_BOTTOM_BANK_TAG, builder);
- }
-
+ if (svtDataList != null) {
+ if (svtDataList.size() > 0) {
+ if (svtDataList.get(0) != null) {
+ this.writeSVTData(svtDataList.get(0));
+ }
+ }
+ }
+ }
+
+ private void writeSVTData(List<HPSSVTData> data) {
+ if (data == null) {
+ throw new RuntimeException("The list points to null.");
+ }
+
+ int nsamples = data.size();
+ int evioIntData[] = new int[nsamples * 4];
+
+ int i = 0;
+ for (HPSSVTData sample : data) {
+ int[] sampleData = sample.getData();
+ //System.out.println(Integer.toHexString(sampleData[0]) + ":" + Integer.toHexString(sampleData[1])+ ":" + Integer.toHexString(sampleData[2])+ ":" + Integer.toHexString(sampleData[3]));
+ evioIntData[i] = sampleData[0];
+ evioIntData[i + 1] = sampleData[1];
+ evioIntData[i + 2] = sampleData[2];
+ evioIntData[i + 3] = sampleData[3];
+ i += 4;
+ }
+ EvioBank bank = new EvioBank(SVT_BANK_TAG, DataType.UINT32, SVT_BANK_NUMBER);
+ try {
+ bank.appendIntData(evioIntData);
+ } catch (EvioException e) {
+ throw new RuntimeException(e);
+ }
+ bank.setAllHeaderLengths();
+ try {
+ builder.addChild(builder.getEvent(), bank);
+ } catch (EvioException e) {
+ throw new RuntimeException(e);
+ }
+ }
+
+ private void writeRawCalorimeterHitCollection(List<RawCalorimeterHit> hits, LCMetaData meta, int bankTag, EventBuilder builder) {
+
+ // Get the ID decoder.
+ IDDecoder dec = meta.getIDDecoder();
+
+ // Make a hit map; allow for multiple hits in a crystal.
+ Map<Long, List<RawCalorimeterHit>> hitMap = new HashMap<Long, List<RawCalorimeterHit>>();
+ for (RawCalorimeterHit hit : hits) {
+ if (hitMap.get(hit.getCellID()) == null) {
+ hitMap.put(hit.getCellID(), new ArrayList<RawCalorimeterHit>());
+ }
+ List<RawCalorimeterHit> channelHits = hitMap.get(hit.getCellID());
+ channelHits.add(hit);
+ }
+
+ // Make map of slot number to hit IDs.
+ Map<Integer, List<Long>> slotMap = new HashMap<Integer, List<Long>>();
+ for (Long id : hitMap.keySet()) {
+ dec.setID(id);
+ int iy = dec.getValue("iy"); // treating as slot number
+ int slot = Math.abs(iy);
+ if (slotMap.get(slot) == null) {
+ slotMap.put(slot, new ArrayList<Long>());
+ }
+ List<Long> slots = slotMap.get(slot);
+ slots.add(id);
+ }
+
+ // Make a new bank for this crate.
+ EvioBank crateBank = new EvioBank(bankTag, DataType.BANK, ECAL_BANK_NUMBER);
+
+ // Loop over the slots in the map.
+ for (int slot : slotMap.keySet()) {
+
+ // New bank for this slot.
+ EvioBank slotBank = new EvioBank(ECAL_PULSE_INTEGRAL_BANK_TAG, DataType.COMPOSITE, slot);
+
+ // Create composite data for this slot and its channels.
+ CompositeData.Data data = new CompositeData.Data();
+ data.addUchar((byte) slot); // slot #
+ data.addUint(0); // trigger #
+ data.addUlong(0); // timestamp
+ List<Long> hitIDs = slotMap.get(slot);
+ int nhits = hitIDs.size();
+ data.addN(nhits); // number of channels
+ for (Long id : hitIDs) {
+ dec.setID(id);
+ int ix = dec.getValue("ix");
+ int channel = ix + ECAL_CHANNEL_OFFSET;
+ data.addUchar((byte) channel); // channel #
+ List<RawCalorimeterHit> channelHits = hitMap.get(id);
+ data.addN(channelHits.size()); // number of pulses
+ for (RawCalorimeterHit hit : channelHits) {
+ data.addUshort((short) hit.getTimeStamp()); // pulse time
+ data.addUint((int) hit.getAmplitude()); // pulse integral
+ }
+ }
+
+ // Add CompositeData to bank.
+ CompositeData cdata = null;
+ try {
+ cdata = new CompositeData(ECAL_PULSE_INTEGRAL_FORMAT, 1, data, ECAL_PULSE_INTEGRAL_BANK_TAG, slot);
+ slotBank.appendCompositeData(cdata);
+ } catch (EvioException e) {
+ throw new RuntimeException(e);
+ }
+
+ // Add slot bank to crate bank.
+ slotBank.setAllHeaderLengths();
+ try {
+ builder.addChild(crateBank, slotBank);
+ } catch (EvioException e) {
+ throw new RuntimeException(e);
+ }
+ }
+ try {
+ crateBank.setAllHeaderLengths();
+ builder.addChild(builder.getEvent(), crateBank);
+ } catch (EvioException e) {
+ throw new RuntimeException(e);
+ }
+ }
+
+ private void writeRawCalorimeterHits(LCMetaData meta, List<RawCalorimeterHit> rawCalorimeterHits, EventBuilder builder) {
+
+ // Make two lists containing the hits from top and bottom sections, which go into separate EVIO data banks.
+ IDDecoder dec = meta.getIDDecoder();
+ List<RawCalorimeterHit> topHits = new ArrayList<RawCalorimeterHit>();
+ List<RawCalorimeterHit> bottomHits = new ArrayList<RawCalorimeterHit>();
+ for (RawCalorimeterHit hit : rawCalorimeterHits) {
+ dec.setID(hit.getCellID());
+ int iy = dec.getValue("iy");
+ // Negative iy should be bottom section.
+ if (iy < 0) {
+ bottomHits.add(hit);
+ } // Positive iy should be top section.
+ else {
+ topHits.add(hit);
+ }
+ }
+
+ // Write the two collections for top and bottom hits to separate EVIO banks.
+ writeRawCalorimeterHitCollection(topHits, meta, ECAL_TOP_BANK_TAG, builder);
+ writeRawCalorimeterHitCollection(bottomHits, meta, ECAL_BOTTOM_BANK_TAG, builder);
+ }
}
\ No newline at end of file
hps-java/src/main/java/org/lcsim/hps/recon/ecal
diff -u -r1.7 -r1.8
--- HPSEcalFADCReadoutDriver.java 19 Jan 2012 18:26:28 -0000 1.7
+++ HPSEcalFADCReadoutDriver.java 1 Apr 2012 21:20:56 -0000 1.8
@@ -1,14 +1,19 @@
package org.lcsim.hps.recon.ecal;
-import java.util.Comparator;
+import java.util.ArrayList;
import java.util.HashMap;
import java.util.LinkedList;
import java.util.List;
import java.util.Map;
import java.util.PriorityQueue;
+import java.util.Set;
import org.lcsim.event.CalorimeterHit;
+import org.lcsim.event.EventHeader;
import org.lcsim.event.RawCalorimeterHit;
+import org.lcsim.event.RawTrackerHit;
+import org.lcsim.event.base.BaseRawTrackerHit;
+import org.lcsim.geometry.subdetector.HPSEcal3;
import org.lcsim.hps.util.ClockSingleton;
import org.lcsim.hps.util.RingBuffer;
import org.lcsim.util.lcio.LCIOConstants;
@@ -18,30 +23,47 @@
* Simulates time evolution of preamp output pulse.
*
* @author Sho Uemura <[log in to unmask]>
- * @version $Id: HPSEcalFADCReadoutDriver.java,v 1.7 2012/01/19 18:26:28 meeg Exp $
+ * @version $Id: HPSEcalFADCReadoutDriver.java,v 1.8 2012/04/01 21:20:56 meeg Exp $
*/
public class HPSEcalFADCReadoutDriver extends HPSEcalReadoutDriver<RawCalorimeterHit> {
- //buffer for deposited energy
- Map<Long, RingBuffer> eDepMap = null;
+ //buffer for deposited energy
+ private Map<Long, RingBuffer> eDepMap = null;
+ //ADC pipeline for readout
+ private Map<Long, FADCPipeline> pipelineMap = null;
//buffer for window sums
- Map<Long, Double> sumMap = null;
+ private Map<Long, Double> sumMap = null;
//buffer for timestamps
- Map<Long, Integer> timeMap = null;
+ private Map<Long, Integer> timeMap = null;
//queue for hits to be output to clusterer
- PriorityQueue<HPSFADCCalorimeterHit> outputQueue = null;
+ private PriorityQueue<HPSFADCCalorimeterHit> outputQueue = null;
//length of ring buffer (in readout cycles)
- int bufferLength = 100;
+ private int bufferLength = 100;
+ //length of readout pipeline (in readout cycles)
+ private int pipelineLength = 2000;
//shaper time constant in ns; negative values generate square pulses of the given width
- double t0 = 18.0;
+ private double t0 = 18.0;
//delay (number of readout periods) between start of summing window and output of hit to clusterer
- int delay0 = 32;
- HPSEcalConverter converter = null;
+ private int delay0 = 32;
+ //start of readout window relative to trigger time (in readout cycles)
+ //in FADC documentation, "Programmable Latency" or PL
+ private int readoutLatency = 200;
+ //number of ADC samples to read out
+ //in FADC documentation, "Programmable Trigger Window" or PTW
+ private int readoutWindow = 64;
+ //number of ADC samples to read out before each pulse maximum
+ //in FADC documentation, "number of samples before" or NSB
+ private int numSamplesBefore = 5;
+ //number of ADC samples to read out before each pulse maximum
+ //in FADC documentation, "number of samples before" or NSA
+ private int numSamplesAfter = 10;
+ private HPSEcalConverter converter = null;
//output buffer for hits
- LinkedList<HPSFADCCalorimeterHit> buffer = new LinkedList<HPSFADCCalorimeterHit>();
+ private LinkedList<HPSFADCCalorimeterHit> buffer = new LinkedList<HPSFADCCalorimeterHit>();
//number of readout periods for which a given hit stays in the buffer
- int coincidenceWindow = 2;
- double pulseIntegral;
+ private int coincidenceWindow = 2;
+ private double pulseIntegral;
+ private String ecalReadoutCollectionName = "EcalReadoutHits";
public HPSEcalFADCReadoutDriver() {
flags = 0;
@@ -50,6 +72,26 @@
converter = new HPSEcalConverter(null);
}
+ public void setEcalReadoutCollectionName(String ecalReadoutCollectionName) {
+ this.ecalReadoutCollectionName = ecalReadoutCollectionName;
+ }
+
+ public void setNumSamplesAfter(int numSamplesAfter) {
+ this.numSamplesAfter = numSamplesAfter;
+ }
+
+ public void setNumSamplesBefore(int numSamplesBefore) {
+ this.numSamplesBefore = numSamplesBefore;
+ }
+
+ public void setReadoutLatency(int readoutLatency) {
+ this.readoutLatency = readoutLatency;
+ }
+
+ public void setReadoutWindow(int readoutWindow) {
+ this.readoutWindow = readoutWindow;
+ }
+
public void setCoincidenceWindow(int coincidenceWindow) {
this.coincidenceWindow = coincidenceWindow;
}
@@ -57,11 +99,11 @@
public void setPedestal(double pedestal) {
converter.setPedestal(pedestal);
}
-
+
public void setScale(double scale) {
converter.setScale(scale);
}
-
+
public void setT0(double t0) {
this.t0 = t0;
}
@@ -73,11 +115,28 @@
public void setBufferLength(int bufferLength) {
this.bufferLength = bufferLength;
eDepMap = new HashMap<Long, RingBuffer>();
+ pipelineMap = new HashMap<Long, FADCPipeline>();
+ }
+
+ public void setPipelineLength(int pipelineLength) {
+ this.pipelineLength = pipelineLength;
+ eDepMap = new HashMap<Long, RingBuffer>();
+ pipelineMap = new HashMap<Long, FADCPipeline>();
}
+ @Override
protected void readHits(List<RawCalorimeterHit> hits) {
+
for (Long cellID : eDepMap.keySet()) {
RingBuffer eDepBuffer = eDepMap.get(cellID);
+
+ FADCPipeline pipeline = pipelineMap.get(cellID);
+ if (pipeline == null) {
+ pipeline = new FADCPipeline(pipelineLength, converter.AtoD(0.0, cellID));
+ pipelineMap.put(cellID, pipeline);
+ }
+ pipeline.writeValue(converter.AtoD(eDepBuffer.currentValue(), cellID));
+
Double sum = sumMap.get(cellID);
if (sum == null && eDepBuffer.currentValue() > threshold) {
timeMap.put(cellID, readoutCounter);
@@ -89,10 +148,11 @@
outputQueue.add(new HPSFADCCalorimeterHit(cellID,
converter.AtoD((sum + eDepBuffer.currentValue()) / pulseIntegral, cellID),
timeMap.get(cellID),
- readoutCounter-timeMap.get(cellID)+1));
+ readoutCounter - timeMap.get(cellID) + 1));
sumMap.remove(cellID);
- } else
+ } else {
sumMap.put(cellID, sum + eDepBuffer.currentValue());
+ }
}
eDepBuffer.step();
}
@@ -100,10 +160,10 @@
if (outputQueue.peek().getTimeStamp() < readoutCounter - delay0) {
System.out.println("Stale hit in output queue");
outputQueue.poll();
- } else
+ } else {
buffer.add(outputQueue.poll());
+ }
}
-
while (!buffer.isEmpty() && buffer.peek().getTimeStamp() <= readoutCounter - delay0 - coincidenceWindow) {
buffer.remove();
}
@@ -111,6 +171,52 @@
hits.addAll(buffer);
}
+ @Override
+ public void startOfData() {
+ super.startOfData();
+ if (ecalReadoutCollectionName == null) {
+ throw new RuntimeException("The parameter ecalReadoutCollectionName was not set!");
+ }
+ }
+
+ @Override
+ public void process(EventHeader event) {
+ super.process(event);
+ //System.out.println(this.getClass().getCanonicalName() + " - process");
+ // Get the list of ECal hits.
+ List<CalorimeterHit> hits = event.get(CalorimeterHit.class, ecalCollectionName);
+ if (hits == null) {
+ throw new RuntimeException("Event is missing ECal hits collection!");
+ }
+
+ if (ClockSingleton.triggered()) {
+ event.put(ecalReadoutCollectionName, readWindow(), RawTrackerHit.class, 0, ecalReadoutName);
+ }
+ }
+
+ protected List<RawTrackerHit> readWindow() {
+ System.out.println("Reading ADC data");
+ List<RawTrackerHit> hits = new ArrayList<RawTrackerHit>();
+
+ Set<Long> cells = ((HPSEcal3) ecal).getNeighborMap().keySet();
+ for (Long cellID : cells) {
+ FADCPipeline pipeline = pipelineMap.get(cellID);
+ short[] adcValues = new short[readoutWindow];
+ if (pipeline == null) {
+ for (int i = 0; i < readoutWindow; i++) {
+ adcValues[i] = (short) converter.AtoD(0.0, cellID);
+ }
+ } else {
+ for (int i = 0; i < readoutWindow; i++) {
+ adcValues[i] = (short) pipeline.getValue(readoutLatency - i);
+ }
+ }
+ hits.add(new BaseRawTrackerHit(cellID, 0, adcValues));
+ }
+ return hits;
+ }
+
+ @Override
protected void putHits(List<CalorimeterHit> hits) {
//fill the readout buffers
for (CalorimeterHit hit : hits) {
@@ -118,6 +224,7 @@
if (eDepBuffer == null) {
eDepBuffer = new RingBuffer(bufferLength);
eDepMap.put(hit.getCellID(), eDepBuffer);
+ pipelineMap.put(hit.getCellID(), new FADCPipeline(pipelineLength, converter.AtoD(0.0, hit.getCellID())));
}
for (int i = 0; i < bufferLength; i++) {
eDepBuffer.addToCell(i, hit.getRawEnergy() * pulseAmplitude((i + 1) * readoutPeriod + readoutTime() - (ClockSingleton.getTime() + hit.getTime())));
@@ -125,9 +232,11 @@
}
}
+ @Override
protected void initReadout() {
//initialize buffers
eDepMap = new HashMap<Long, RingBuffer>();
+ pipelineMap = new HashMap<Long, FADCPipeline>();
sumMap = new HashMap<Long, Double>();
timeMap = new HashMap<Long, Integer>();
outputQueue = new PriorityQueue(20, new HPSFADCCalorimeterHit.TimeComparator());
@@ -135,15 +244,65 @@
}
private double pulseAmplitude(double time) {
- if (time < 0.0)
+ if (time < 0.0) {
return 0.0;
+ }
if (t0 > 0.0) {
return (time / t0) * Math.exp(1.0 - time / t0);
} else {
- if (time < -t0)
+ if (time < -t0) {
return 1.0;
- else
+ } else {
return 0.0;
+ }
+ }
+ }
+
+ private class FADCPipeline {
+
+ private int[] array;
+ private int size;
+ private int ptr;
+
+ public FADCPipeline(int size) {
+ this.size = size;
+ array = new int[size]; //initialized to 0
+ ptr = 0;
+ }
+
+ //construct pipeline with a nonzero initial value
+ public FADCPipeline(int size, int init) {
+ this.size = size;
+ array = new int[size];
+ for (int i = 0; i < size; i++) {
+ array[i] = init;
+ }
+ ptr = 0;
+ }
+
+ /**
+ * Write value to current cell
+ */
+ public void writeValue(int val) {
+ array[ptr] = val;
+ }
+
+ /**
+ * Write value to current cell
+ */
+ public void step() {
+ ptr++;
+ if (ptr == size) {
+ ptr = 0;
+ }
+ }
+
+ //return content of specified cell (pos=0 for current cell)
+ public int getValue(int pos) {
+ if (pos > size) {
+ throw new ArrayIndexOutOfBoundsException();
+ }
+ return array[((ptr - pos) % size + size) % size];
}
}
-}
+}
\ No newline at end of file