Skip to content
Snippets Groups Projects
Commit e66e8e00 authored by Loïc Le Guyader's avatar Loïc Le Guyader
Browse files

Merge branch 'FastADC' into 'master'

Fast adc

See merge request SCS/ToolBox!28
parents 3c20bb31 26e783a7
No related branches found
No related tags found
No related merge requests found
...@@ -116,6 +116,14 @@ mnemonics = { ...@@ -116,6 +116,14 @@ mnemonics = {
"VFM_BENDERF": {'source':'SCS_KBS_VFM/MOTOR/BENDERF', "VFM_BENDERF": {'source':'SCS_KBS_VFM/MOTOR/BENDERF',
'key':'encoderPosition.value', 'key':'encoderPosition.value',
'dim':None}, 'dim':None},
# LASER TIMING
"AFS_PhaseShifter": {'source':'SCS_ILH_LAS/PHASESHIFTER/DOOCS',
'key':'actualPosition.value',
'dim':None},
"AFS_DelayLine": {'source':'SCS_ILH_LAS/MOTOR/LT3',
'key':'AActualPosition.value',
'dim':None},
# FFT # FFT
"scannerX": {'source':'SCS_CDIFFT_SAM/LMOTOR/SCANNERX', "scannerX": {'source':'SCS_CDIFFT_SAM/LMOTOR/SCANNERX',
...@@ -192,6 +200,68 @@ mnemonics = { ...@@ -192,6 +200,68 @@ mnemonics = {
'key':'digitizers.channel_1_A.raw.samples', 'key':'digitizers.channel_1_A.raw.samples',
'dim': ['samplesId']}, 'dim': ['samplesId']},
# FastADC
"FastADC0peaks": {'source':'SCS_UTC1_MCP/ADC/1:channel_0.output',
'key':'data.peaks',
'dim':['peakId']},
"FastADC0raw": {'source':'SCS_UTC1_MCP/ADC/1:channel_0.output',
'key':'data.rawData',
'dim':['samplesId']},
"FastADC1peaks": {'source':'SCS_UTC1_MCP/ADC/1:channel_1.output',
'key':'data.peaks',
'dim':['peakId']},
"FastADC1raw": {'source':'SCS_UTC1_MCP/ADC/1:channel_1.output',
'key':'data.rawData',
'dim':['samplesId']},
"FastADC2peaks": {'source':'SCS_UTC1_MCP/ADC/1:channel_2.output',
'key':'data.peaks',
'dim':['peakId']},
"FastADC2raw": {'source':'SCS_UTC1_MCP/ADC/1:channel_2.output',
'key':'data.rawData',
'dim':['samplesId']},
"FastADC3peaks": {'source':'SCS_UTC1_MCP/ADC/1:channel_3.output',
'key':'data.peaks',
'dim':['peakId']},
"FastADC3raw": {'source':'SCS_UTC1_MCP/ADC/1:channel_3.output',
'key':'data.rawData',
'dim':['samplesId']},
"FastADC4peaks": {'source':'SCS_UTC1_MCP/ADC/1:channel_4.output',
'key':'data.peaks',
'dim':['peakId']},
"FastADC4raw": {'source':'SCS_UTC1_MCP/ADC/1:channel_4.output',
'key':'data.rawData',
'dim':['samplesId']},
"FastADC5peaks": {'source':'SCS_UTC1_MCP/ADC/1:channel_5.output',
'key':'data.peaks',
'dim':['peakId']},
"FastADC5raw": {'source':'SCS_UTC1_MCP/ADC/1:channel_5.output',
'key':'data.rawData',
'dim':['samplesId']},
"FastADC6peaks": {'source':'SCS_UTC1_MCP/ADC/1:channel_6.output',
'key':'data.peaks',
'dim':['peakId']},
"FastADC6raw": {'source':'SCS_UTC1_MCP/ADC/1:channel_6.output',
'key':'data.rawData',
'dim':['samplesId']},
"FastADC7peaks": {'source':'SCS_UTC1_MCP/ADC/1:channel_7.output',
'key':'data.peaks',
'dim':['peakId']},
"FastADC7raw": {'source':'SCS_UTC1_MCP/ADC/1:channel_7.output',
'key':'data.rawData',
'dim':['samplesId']},
"FastADC8peaks": {'source':'SCS_UTC1_MCP/ADC/1:channel_8.output',
'key':'data.peaks',
'dim':['peakId']},
"FastADC8raw": {'source':'SCS_UTC1_MCP/ADC/1:channel_8.output',
'key':'data.rawData',
'dim':['samplesId']},
"FastADC9peaks": {'source':'SCS_UTC1_MCP/ADC/1:channel_9.output',
'key':'data.peaks',
'dim':['peakId']},
"FastADC9raw": {'source':'SCS_UTC1_MCP/ADC/1:channel_9.output',
'key':'data.rawData',
'dim':['samplesId']},
# KARABACON # KARABACON
"KARABACON": {'source':'SCS_DAQ_SCAN/MDL/KARABACON', "KARABACON": {'source':'SCS_DAQ_SCAN/MDL/KARABACON',
'key': 'actualStep.value', 'key': 'actualStep.value',
......
...@@ -10,6 +10,7 @@ import numpy as np ...@@ -10,6 +10,7 @@ import numpy as np
import xarray as xr import xarray as xr
# Machine
def pulsePatternInfo(data, plot=False): def pulsePatternInfo(data, plot=False):
''' display general information on the pulse patterns operated by SASE1 and SASE3. ''' display general information on the pulse patterns operated by SASE1 and SASE3.
This is useful to track changes of number of pulses or mode of operation of This is useful to track changes of number of pulses or mode of operation of
...@@ -114,6 +115,7 @@ def repRate(data, sase='sase3'): ...@@ -114,6 +115,7 @@ def repRate(data, sase='sase3'):
return f return f
# XGM
def selectSASEinXGM(data, sase='sase3', xgm='SCS_XGM', sase3First=True, npulses=None): def selectSASEinXGM(data, sase='sase3', xgm='SCS_XGM', sase3First=True, npulses=None):
''' Extract SASE1- or SASE3-only XGM data. ''' Extract SASE1- or SASE3-only XGM data.
There are various cases depending on i) the mode of operation (10 Hz There are various cases depending on i) the mode of operation (10 Hz
...@@ -385,6 +387,7 @@ def calibrateXGMs(data, rollingWindow=200, plot=False): ...@@ -385,6 +387,7 @@ def calibrateXGMs(data, rollingWindow=200, plot=False):
return np.array([sa3_calib_factor, scs_calib_factor]) return np.array([sa3_calib_factor, scs_calib_factor])
# TIM
def mcpPeaks(data, intstart, intstop, bkgstart, bkgstop, mcp=1, t_offset=None, npulses=None): def mcpPeaks(data, intstart, intstop, bkgstart, bkgstop, mcp=1, t_offset=None, npulses=None):
''' Computes peak integration from raw MCP traces. ''' Computes peak integration from raw MCP traces.
...@@ -844,4 +847,93 @@ def matchXgmTimPulseId(data, use_apd=True, intstart=None, intstop=None, ...@@ -844,4 +847,93 @@ def matchXgmTimPulseId(data, use_apd=True, intstart=None, intstop=None,
dropList.append('MCP{}apd'.format(mcp)) dropList.append('MCP{}apd'.format(mcp))
mergeList.append(data.drop(dropList)) mergeList.append(data.drop(dropList))
subset = xr.merge(mergeList, join='inner') subset = xr.merge(mergeList, join='inner')
subset.attrs['run'] = data.attrs['run']
return subset return subset
# Fast ADC
def fastAdcPeaks(data, channel, intstart, intstop, bkgstart, bkgstop, period=None, npulses=None):
''' Computes peak integration from raw FastADC traces.
Inputs:
data: xarray Dataset containing FastADC raw traces (e.g. 'FastADC1raw')
channel: FastADC channel number
intstart: trace index of integration start
intstop: trace index of integration stop
bkgstart: trace index of background start
bkgstop: trace index of background stop
period: number of samples between two pulses. Needed if bunch
pattern info is not available. If None, checks the pulse
pattern and determine the period assuming a resolution of
9.23 ns per sample which leads to 24 samples between
two bunches @ 4.5 MHz.
npulses: number of pulses. If None, takes the maximum number of
pulses according to the bunch patter (field 'npulses_sase3')
Output:
results: DataArray with dims trainId x max(sase3 pulses)
'''
keyraw = 'FastADC{}raw'.format(channel)
if keyraw not in data:
raise ValueError("Source not found: {}!".format(keyraw))
if npulses is None:
npulses = int(data['npulses_sase3'].max().values)
if period is None:
sa3 = data['sase3'].where(data['sase3']>1)
if npulses > 1:
#Calculate the number of pulses between two lasing pulses (step)
step = sa3.where(data['npulses_sase3']>1, drop=True)[0,:2].values
step = int(step[1] - step[0])
#multiply by elementary pulse length (221.5 ns / 9.23 ns = 24 samples)
period = 24 * step
else:
period = 1
results = xr.DataArray(np.empty((data.trainId.shape[0], npulses)), coords=data[keyraw].coords,
dims=['trainId', 'peakId'.format(channel)])
for i in range(npulses):
a = intstart + period*i
b = intstop + period*i
bkga = bkgstart + period*i
bkgb = bkgstop + period*i
bg = np.outer(np.median(data[keyraw][:,bkga:bkgb], axis=1), np.ones(b-a))
integ = np.trapz(data[keyraw][:,a:b] - bg, axis=1)
results[:,i] = integ
return results
def mergeFastAdcPeaks(data, channel, intstart, intstop, bkgstart, bkgstop,
period=None, npulses=None, dim='lasPulseId'):
''' Calculates the peaks from Fast ADC raw traces with fastAdcPeaks()
and merges the results in Dataset.
Inputs:
data: xr Dataset with 'FastADC[channel]raw' traces
channel: Fast ADC channel
intstart: trace index of integration start
intstop: trace index of integration stop
bkgstart: trace index of background start
bkgstop: trace index of background stop
period: Number of samples separation between two pulses. Needed
if bunch pattern info is not available. If None, checks the
pulse pattern and determine the period assuming a resolution
of 9.23 ns per sample which leads to 24 samples between
two bunches @ 4.5 MHz.
npulses: number of pulses. If None, takes the maximum number of
pulses according to the bunch patter (field 'npulses_sase3')
dim: name of the xr dataset dimension along the peaks
'''
peaks = fastAdcPeaks(data, channel=channel, intstart=intstart, intstop=intstop,
bkgstart=bkgstart, bkgstop=bkgstop, period=period,
npulses=npulses)
key = 'FastADC{}peaks'.format(channel)
if key in data:
s = data.drop(key)
else:
s = data
peaks = peaks.rename(key).rename({'peakId':dim})
subset = xr.merge([s, peaks], join='inner')
subset.attrs['run'] = data.attrs['run']
return subset
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment