def tt_config(cl,connect_str,cfgtype,detname,detsegm,grp): global group global ocfg group = grp cfg = get_config(connect_str,cfgtype,detname,detsegm) ocfg = cfg user_to_expert(cl,cfg,full=True) # set bool parameters cfg['expert']['ClinkFeb']['TrigCtrl']['EnableTrig'] = True cfg['expert']['ClinkFeb']['TrigCtrl']['InvCC'] = False cfg['expert']['ClinkFeb']['ClinkTop']['ClinkCh']['DataEn'] = True cfg['expert']['ClinkFeb']['ClinkTop']['ClinkCh']['Blowoff'] = False uart = getattr(getattr(cl,'ClinkFeb[%d]'%lane).ClinkTop,'Ch[%d]'%chan).UartPiranha4 getattr(getattr(cl,'ClinkFeb[%d]'%lane).ClinkTop,'Ch[%d]'%chan).UartPiranha4.SendEscape() config_expert(cl,cfg) #commands can be sent manually using cl.ClinkFeb0.ClinkTop.Ch0.UartPiranha4._tx.sendString('GCP') # GCP returns configuration summary uart._tx.sendString('gcp') cl_poll(uart) #cl.TimeToolKcu1500.Kcu1500Hsio.TimingRx.XpmMiniWrapper.XpmMini.HwEnable.set(True) getattr(cl.TimeToolKcu1500.Kcu1500Hsio.TimingRx.TriggerEventManager,'TriggerEventBuffer[%d]'%lane).MasterEnable.set(True) # Capture the firmware version to persist in the xtc cfg['firmwareVersion'] = cl.TimeToolKcu1500.AxiPcieCore.AxiVersion.FpgaVersion.get() cfg['firmwareBuild' ] = cl.TimeToolKcu1500.AxiPcieCore.AxiVersion.BuildStamp.get() return json.dumps(cfg)
def tb_config(base,connect_str,cfgtype,detname,detsegm,rog): global ocfg global pv_prefix global readout_groups print('tb_config') cfg = get_config(connect_str,cfgtype,detname,detsegm) ocfg = cfg # get the list of readout groups that the user has selected # so we only configure those readout_groups = [] connect_info = json.loads(connect_str) for nodes in connect_info['body']['drp'].values(): readout_groups.append(nodes['det_info']['readout']) readout_groups = set(readout_groups) print(f'readout_groups {readout_groups} min {min(readout_groups)}') control_info = connect_info['body']['control']['0']['control_info'] xpm_master = control_info['xpm_master'] pv_prefix = control_info['pv_base']+':XPM:'+str(xpm_master)+':' teb = getattr(base['pcie'].DevPcie.Hsio.TimingRx.TriggerEventManager,f'TriggerEventBuffer[{lane}]') teb.Partition.set(min(readout_groups)) teb.TriggerDelay.set(0) base['pcie'].StartRun() return apply_config(cfg, detsegm==0)
def tt_config(cl,connect_str,cfgtype,detname,detsegm,group): cfg = get_config(connect_str,cfgtype,detname,detsegm) # TimeToolKcu1500Root.TimeToolKcu1500.Kcu1500Hsio.TimingRx.TriggerEventManager.XpmMessageAligner.RxId partitionDelay = getattr(cl.TimeToolKcu1500.Kcu1500Hsio.TimingRx.TriggerEventManager.XpmMessageAligner,'PartitionDelay[%d]'%group).get() rawStart = cfg['user']['start_ns'] triggerDelay = int(rawStart*1300/7000 - partitionDelay*200) print('partitionDelay {:} rawStart {:} triggerDelay {:}'.format(partitionDelay,rawStart,triggerDelay)) if triggerDelay < 0: print('partitionDelay {:} rawStart {:} triggerDelay {:}'.format(partitionDelay,rawStart,triggerDelay)) raise ValueError('triggerDelay computes to < 0') cfg['cl']['TimeToolKcu1500']['Kcu1500Hsio']['TimingRx']['TriggerEventManager']['TriggerEventBuffer0']['TriggerDelay'] = triggerDelay cfg['cl']['TimeToolKcu1500']['Kcu1500Hsio']['TimingRx']['TriggerEventManager']['TriggerEventBuffer0']['Partition'] = group cl.ClinkFeb[0].ClinkTop.Ch[0].UartPiranha4.SendEscape() depth = 0 path = 'cl' my_queue = deque([[path,depth,cl,cfg['cl']]]) #contains path, dfs depth, rogue hiearchy, and daq configdb dict tree node kludge_dict = {"TriggerEventBuffer0":"TriggerEventBuffer[0]","AppLane0":"AppLane[0]","ClinkFeb0":"ClinkFeb[0]","Ch0":"Ch[0]", "ROI0":"ROI[0]","ROI1":"ROI[1]","SAD0":"SAD[0]","SAD1":"SAD[1]","SAD2":"SAD[2]"} while(my_queue): path,depth,rogue_node, configdb_node = my_queue.pop() if(dict is type(configdb_node)): for i in configdb_node: if i in kludge_dict: my_queue.appendleft([path+"."+i,depth+1,rogue_node.nodes[kludge_dict[i]],configdb_node[i]]) else: my_queue.appendleft([path+"."+i,depth+1,rogue_node.nodes[i],configdb_node[i]]) if('get' in dir(rogue_node) and 'set' in dir(rogue_node) and path is not 'cl' ): # All FIR parameters are stored in configdb as hex strings (I don't know why) if ".FIR." in path: print(path+", rogue value = "+str(hex(rogue_node.get()))+", daq config database = " +str(configdb_node)) rogue_node.set(int(str(configdb_node),16)) else: rogue_node.set(configdb_node) #cl.TimeToolKcu1500.Kcu1500Hsio.TimingRx.XpmMiniWrapper.XpmMini.HwEnable.set(True) cl.TimeToolKcu1500.Kcu1500Hsio.TimingRx.TriggerEventManager.TriggerEventBuffer[0].MasterEnable.set(True) # Capture the firmware version to persist in the xtc cfg['firmwareVersion'] = cl.TimeToolKcu1500.AxiPcieCore.AxiVersion.FpgaVersion.get() cfg['firmwareBuild' ] = cl.TimeToolKcu1500.AxiPcieCore.AxiVersion.BuildStamp.get() return json.dumps(cfg)
def wave8_config(prefix, connect_str, cfgtype, detname, detsegm, grp): global ctxt global lane global group group = grp cfg = get_config(connect_str, cfgtype, detname, detsegm) ocfg = cfg ctxt = Context('pva') epics_prefix = prefix + ':Top:' user_to_expert(ctxt, epics_prefix, cfg, full=True) # Assert clears names_clr = [ epics_prefix + 'BatcherEventBuilder:Blowoff', epics_prefix + 'TimingFrameRx:RxCountReset', epics_prefix + 'RawBuffers:CntRst', epics_prefix + 'Integrators:CntRst' ] values = [1] * len(names_clr) print('names {:}'.format(names_clr)) ctxt.put(names_clr, values) config_expert(ctxt, epics_prefix, cfg['expert']) ctxt.put(epics_prefix + 'TriggerEventManager:TriggerEventBuffer[%d]:MasterEnable' % lane, 1, wait=True) time.sleep(0.2) # Deassert clears values = [0] * len(names_clr) print('names {:}'.format(names_clr)) ctxt.put(names_clr, values) ctxt.put(epics_prefix + 'BatcherEventBuilder:Blowoff', 0, wait=True) cfg['firmwareVersion'] = ctxt.get(epics_prefix + 'AxiVersion:FpgaVersion').raw.value cfg['firmwareBuild'] = ctxt.get(epics_prefix + 'AxiVersion:BuildStamp').raw.value ctxt.close() v = json.dumps(cfg) return v
def ts_config(connect_json, cfgtype, detname, detsegm): global ocfg global pv_prefix global readout_groups cfg = get_config(connect_json, cfgtype, detname, detsegm) ocfg = cfg connect_info = json.loads(connect_json) # get the list of readout groups that the user has selected # so we only configure those readout_groups = [] connect_info = json.loads(connect_json) for nodes in connect_info['body']['drp'].values(): readout_groups.append(nodes['det_info']['readout']) readout_groups = set(readout_groups) control_info = connect_info['body']['control']['0']['control_info'] xpm_master = control_info['xpm_master'] pv_prefix = control_info['pv_base'] + ':XPM:' + str(xpm_master) + ':' return apply_config(cfg)
def wave8_config(base,connect_str,cfgtype,detname,detsegm,grp): global lane global group global ocfg global timebase print(f'base [{base}]') prefix = base['prefix'] timebase = base['timebase'] group = grp # Read the configdb cfg = get_config(connect_str,cfgtype,detname,detsegm) ocfg = cfg # Apply the user configs epics_prefix = prefix + ':Top:' user_to_expert(epics_prefix, cfg, full=True) # Assert clears names_clr = [epics_prefix+'BatcherEventBuilder:Blowoff', # epics_prefix+'TimingFrameRx:RxCountReset', epics_prefix+'RawBuffers:CntRst', epics_prefix+'Integrators:CntRst'] values = [1]*len(names_clr) ctxt_put(names_clr,values) names_cfg = [epics_prefix+'TriggerEventManager:TriggerEventBuffer[0]:Partition', epics_prefix+'TriggerEventManager:TriggerEventBuffer[0]:PauseThreshold', epics_prefix+'TriggerEventManager:TriggerEventBuffer[0]:MasterEnable'] values = [group,16,1] ctxt_put(names_cfg, values) time.sleep(0.2) # Deassert clears values = [0]*len(names_clr) ctxt_put(names_clr,values) # # Now construct the configuration we will record # top = cdict() top.setAlg('config', [2,0,0]) detname = cfg['detName:RO'].rsplit('_',1) top.setInfo(detType='wave8', detName=detname[0], detSegm=int(detname[1]), detId=cfg['detId:RO'], doc='No comment') top.define_enum('baselineEnum', {'_%d_samples'%(2**key):key for key in range(1,8)}) top.define_enum('quadrantEnum', {'Even':0, 'Odd':1}) top.set("firmwareBuild:RO" , "-", 'CHARSTR') top.set("firmwareVersion:RO", 0, 'UINT32') top.set("expert.SystemRegs.AvccEn0" , 1,'UINT8') top.set("expert.SystemRegs.AvccEn1" , 1,'UINT8') top.set("expert.SystemRegs.Ap5V5En" , 1,'UINT8') top.set("expert.SystemRegs.Ap5V0En" , 1,'UINT8') top.set("expert.SystemRegs.A0p3V3En" , 1,'UINT8') top.set("expert.SystemRegs.A1p3V3En" , 1,'UINT8') top.set("expert.SystemRegs.Ap1V8En" , 1,'UINT8') top.set("expert.SystemRegs.FpgaTmpCritLatch", 0,'UINT8') top.set("expert.SystemRegs.AdcCtrl1" , 0,'UINT8') top.set("expert.SystemRegs.AdcCtrl2" , 0,'UINT8') top.set("expert.SystemRegs.TrigEn" , 0,'UINT8') top.set("expert.SystemRegs.timingRxUserRst" , 0,'UINT8') top.set("expert.SystemRegs.timingTxUserRst" , 0,'UINT8') top.set("expert.SystemRegs.timingUseMiniTpg", 0,'UINT8') top.set("expert.SystemRegs.TrigSrcSel" , 1,'UINT8') top.set("expert.Integrators.TrigDelay" , 0,'UINT32') # user config top.set("expert.Integrators.IntegralSize" , 0,'UINT32') # user config top.set("expert.Integrators.BaselineSize" , 0,'UINT8') # user config top.set("expert.Integrators.QuadrantSel" , 0,'quadrantEnum') # user config top.set("expert.Integrators.CorrCoefficientFloat64", [1.0]*4, 'DOUBLE') # user config top.set("expert.Integrators.ProcFifoPauseThreshold", 255,'UINT32') top.set("expert.Integrators.IntFifoPauseThreshold" , 255,'UINT32') top.set("expert.RawBuffers.BuffEn" ,[0]*8,'UINT32') # user config top.set("expert.RawBuffers.BuffLen" , 100,'UINT32') # user config top.set("expert.RawBuffers.FifoPauseThreshold", 100,'UINT32') top.set("expert.RawBuffers.TrigPrescale" , 0,'UINT32') # user config top.set("expert.BatcherEventBuilder.Bypass" , 0,'UINT8') top.set("expert.BatcherEventBuilder.Timeout", 0,'UINT32') top.set("expert.BatcherEventBuilder.Blowoff", 0,'UINT8') top.set("expert.TriggerEventManager.TriggerEventBuffer.TriggerDelay" , 0,'UINT32') # user config dlyAlane = [ [ 0x0c,0x0b,0x0e,0x0e,0x10,0x10,0x12,0x0b ], [ 0x0a,0x08,0x0c,0x0b,0x0d,0x0c,0x0b,0x0c ], [ 0x12,0x13,0x13,0x13,0x13,0x13,0x13,0x13 ], [ 0x0d,0x0c,0x0d,0x0b,0x0a,0x12,0x12,0x13 ] ] dlyBlane = [ [ 0x11,0x11,0x12,0x12,0x10,0x11,0x0b,0x0b ], [ 0x0a,0x0a,0x0c,0x0c,0x0c,0x0b,0x0b,0x0a ], [ 0x14,0x14,0x14,0x14,0x14,0x12,0x10,0x11 ], [ 0x13,0x12,0x13,0x12,0x12,0x11,0x12,0x11 ] ] for iadc in range(4): adc = 'AdcReadout%d'%iadc top.set('expert.'+adc+'.DelayAdcALane', dlyAlane[iadc], 'UINT8') top.set('expert.'+adc+'.DelayAdcBLane', dlyBlane[iadc], 'UINT8') top.set('expert.'+adc+'.DMode' , 3, 'UINT8') top.set('expert.'+adc+'.Invert' , 0, 'UINT8') top.set('expert.'+adc+'.Convert', 3, 'UINT8') for iadc in range(4): adc = 'AdcConfig%d'%iadc zeroregs = [7,8,0xb,0xc,0xf,0x10,0x11,0x12,0x12,0x13,0x14,0x16,0x17,0x18,0x20] for r in zeroregs: top.set('expert.'+adc+'.AdcReg_0x%04X'%r, 0, 'UINT8') top.set('expert.'+adc+'.AdcReg_0x0006' , 0x80, 'UINT8') top.set('expert.'+adc+'.AdcReg_0x000D' , 0x6c, 'UINT8') top.set('expert.'+adc+'.AdcReg_0x0015' , 1, 'UINT8') top.set('expert.'+adc+'.AdcReg_0x001F' , 0xff, 'UINT8') top.set('expert.AdcPatternTester.Channel', 0, 'UINT8' ) top.set('expert.AdcPatternTester.Mask' , 0, 'UINT8' ) top.set('expert.AdcPatternTester.Pattern', 0, 'UINT8' ) top.set('expert.AdcPatternTester.Samples', 0, 'UINT32' ) top.set('expert.AdcPatternTester.Request', 0, 'UINT8' ) scfg = top.typed_json() # # Retrieve full configuration for recording # d = epics_get(scfg['expert']) keys = [key for key,v in d.items()] names = [epics_prefix+v for key,v in d.items()] values = ctxt_get(names) for i,v in enumerate(values): k = keys[i].split('.') c = scfg['expert'] while len(k)>1: c = c[k[0]] del k[0] if k[0][0]=='[': elem = int(k[0][1:-1]) c[elem] = v else: c[k[0]] = v scfg['firmwareVersion:RO'] = ctxt_get(prefix+':AxiVersion:FpgaVersion') #scfg['firmwareBuild:RO' ] = ctxt_get(prefix+':AxiVersion:BuildStamp') pprint.pprint(scfg) v = json.dumps(scfg) if 'pci' in base: # Note that other segment levels can step on EventBuilder settings (Bypass,VcDataTap) pbase = base['pci'] getattr(pbase.DevPcie.Application,f'AppLane[{lane}]').VcDataTap.Tap.set(1) eventBuilder = getattr(pbase.DevPcie.Application,f'AppLane[{lane}]').EventBuilder eventBuilder.Bypass.set(5) eventBuilder.Blowoff.set(False) eventBuilder.SoftRst() return v
def opal_config(cl, connect_str, cfgtype, detname, detsegm, grp): global ocfg global group global lane global chan group = grp appLane = 'AppLane[%d]' % lane clinkFeb = 'ClinkFeb[%d]' % lane clinkCh = 'Ch[%d]' % chan cfg = get_config(connect_str, cfgtype, detname, detsegm) ocfg = cfg if (cl.ClinkPcie.Hsio.PgpMon[0].RxRemLinkReady.get() != 1): raise ValueError(f'PGP Link is down') # drain any data in the event pipeline getattr(cl.ClinkPcie.Application, appLane).EventBuilder.Blowoff.set(True) getattr(getattr(cl, clinkFeb).ClinkTop, clinkCh).Blowoff.set(True) # set bool parameters cfg['expert']['ClinkFeb']['TrigCtrl']['EnableTrig'] = True cfg['expert']['ClinkFeb']['TrigCtrl']['InvCC'] = False cfg['expert']['ClinkFeb']['ClinkTop']['ClinkCh']['DataEn'] = True # trigger polarity inversion for firmware version uart = getattr(getattr(cl, clinkFeb).ClinkTop, clinkCh).UartOpal1000 try: v = uart.BS.get() uart.BS.set(str(int(v) + 1)) except: uart.BS.set('0') time.sleep(0.10) fwver = uart._rx._last.split(';') if len(fwver) > 2: major, minor = fwver[2].split('.')[:2] # CCE is a special command in the rogue surf. it waits for # both CCE[0] and CCE[1] to be filled in before transmitting. # a possible issue: when we do a second configure, the # fields will be non-empty, so we think we will do two # uart writes of the same value. not ideal, but should be ok. # we inherited this information about firmware version # numbers from LCLS1, but we are not confident it is solid. # for a given camera, the exposure time should be checked # by looking at the second set of 4 pixels of an image after # a long time between triggers which have an exposure time # measurement. CCE[1] is the "polarity" portion of CCE: # cpo: somehow this logic is wrong because this response # from a camera's BS command @"1.10;1.11;1.11 wanted # normal polarity, but the exposure time (after a pause) # was very large. So hardwire inverted-polarity for now. #if int(major)<1 or (int(major)==1 and int(minor)<20): # print('Normal polarity') # getattr(uart,'CCE[1]').set(0) #else: # print('Inverted polarity') # getattr(uart,'CCE[1]').set(1) print('Inverted polarity') getattr(uart, 'CCE[1]').set(1) # CCE[0] is the "trigger input source" portion of CCE. getattr(uart, 'CCE[0]').set(0) # trigger on CC1 uart.MO.set(1) # set to triggered mode user_to_expert(cl, cfg, full=True) config_expert(cl, cfg['expert']) cl.ClinkPcie.Hsio.TimingRx.XpmMiniWrapper.XpmMini.HwEnable.set(True) cl.ClinkPcie.Hsio.TimingRx.TriggerEventManager.TriggerEventBuffer[ 0].MasterEnable.set(True) getattr(getattr(cl, clinkFeb).ClinkTop, clinkCh).Blowoff.set(False) getattr(cl.ClinkPcie.Application, appLane).EventBuilder.Blowoff.set(False) # Capture the firmware version to persist in the xtc cfg['firmwareVersion'] = cl.ClinkPcie.AxiPcieCore.AxiVersion.FpgaVersion.get( ) cfg['firmwareBuild'] = cl.ClinkPcie.AxiPcieCore.AxiVersion.BuildStamp.get() cl.StartRun() ocfg = cfg return json.dumps(cfg)
def wave8_config(prefix,connect_str,cfgtype,detname,detsegm,group): global ctxt cfg = get_config(connect_str,cfgtype,detname,detsegm) ctxt = Context('pva') # | timing fiducial # PartitionDelay | TriggerEventManager.TriggerEventBuffer receives xpm trigger # TriggerDelay | TriggerEventManager.triggerBus asserts trigger # IntStart | Integrators.intStart (baseline latched) # IntLen | Intregrators.intEnd # | RawDataBuffer start # RawBuffLen | RawDataBuffer End epics_prefix = prefix + ':Top:' partitionDelay = ctxt.get(epics_prefix+'TriggerEventManager:XpmMessageAligner:PartitionDelay[%d]'%group) raw = cfg['user']['raw'] rawStart = raw['start_ns'] triggerDelay = rawStart*1300/7000 - partitionDelay*200 print('partitionDelay {:} rawStart {:} triggerDelay {:}'.format(partitionDelay,rawStart,triggerDelay)) if triggerDelay < 0: raise ValueError('triggerDelay computes to < 0') rawNsamples = int(raw['gate_ns']*0.25) if rawNsamples>256: raise ValueError('raw.gate_ns > 1020') raw['nsamples'] = rawNsamples fex = cfg['user']['fex'] intStart = fex['start_ns'] if intStart < rawStart: print('fex.start_ns {:} raw.start_ns {:}'.format(intStart,rawStart)) raise ValueError('fex.start_ns < raw.start_ns') fexTrigDelay = int((intStart-rawStart)*250/1000) if fexTrigDelay > 255: raise ValueError('fex.start_ns > raw.start_ns + 1020') fexNsamples = int(fex['gate_ns']*0.25) if fexNsamples>255: raise ValueError('fex.gate_ns > 1020') fex['nsamples'] = rawNsamples # Assert clears names_clr = [epics_prefix+'BatcherEventBuilder:Blowoff', epics_prefix+'TimingFrameRx:RxCountReset', epics_prefix+'RawBuffers:CntRst', epics_prefix+'Integrators:CntRst'] values = [1]*len(names_clr) print('names {:}'.format(names_clr)) ctxt.put(names_clr,values) expert = cfg['expert']['Top'] expert['TriggerEventManager']['TriggerEventBuffer[0]']['TriggerDelay'] = triggerDelay for i in range(8): expert['RawBuffers']['BuffEn[%d]'%i] = raw['enable[%d]'%i] # Firmware needs a value one less expert['RawBuffers']['BuffLen'] = rawNsamples-1 # Firmware needs a value one less prescale = raw['prescale'] if prescale>0: prescale -= 1 expert['RawBuffers']['TrigPrescale'] = prescale expert['Integrators']['TrigDelay'] = fexTrigDelay # Firmware needs a value one less expert['Integrators']['IntegralSize'] = fexNsamples-1 expert['Integrators']['BaselineSize'] = fex['baseline'] for i in range(4): expert['Integrators']['CorrCoefficientFloat64[%d]'%i] = fex['coeff[%d]'%i] expert['TriggerEventManager']['TriggerEventBuffer[0]']['Partition'] = group names = [] values = [] epics_put(cfg['expert'],prefix+':',names,values) ctxt.put(names,values) ctxt.put(epics_prefix+'TriggerEventManager:TriggerEventBuffer[0]:MasterEnable', 1, wait=True) time.sleep(0.2) # Deassert clears values = [0]*len(names_clr) ctxt.put(names_clr,values) ctxt.put(epics_prefix+'BatcherEventBuilder:Blowoff', 0, wait=True) cfg['firmwareVersion'] = ctxt.get(epics_prefix+'AxiVersion:FpgaVersion').raw.value cfg['firmwareBuild' ] = ctxt.get(epics_prefix+'AxiVersion:BuildStamp').raw.value ctxt.close() v = json.dumps(cfg) return v
def tt_config(cl, connect_str, cfgtype, detname, detsegm, group): cfg = get_config(connect_str, cfgtype, detname, detsegm) # TimeToolKcu1500Root.TimeToolKcu1500.Kcu1500Hsio.TimingRx.TriggerEventManager.XpmMessageAligner.RxId partitionDelay = getattr( cl.TimeToolKcu1500.Kcu1500Hsio.TimingRx.TriggerEventManager. XpmMessageAligner, 'PartitionDelay[%d]' % group).get() rawStart = cfg['user']['start_ns'] triggerDelay = int(rawStart * 1300 / 7000 - partitionDelay * 200) print('partitionDelay {:} rawStart {:} triggerDelay {:}'.format( partitionDelay, rawStart, triggerDelay)) if triggerDelay < 0: print('partitionDelay {:} rawStart {:} triggerDelay {:}'.format( partitionDelay, rawStart, triggerDelay)) raise ValueError('triggerDelay computes to < 0') cfg['expert']['TimeToolKcu1500']['Kcu1500Hsio']['TimingRx'][ 'TriggerEventManager']['TriggerEventBuffer[0]'][ 'TriggerDelay'] = triggerDelay cfg['expert']['TimeToolKcu1500']['Kcu1500Hsio']['TimingRx'][ 'TriggerEventManager']['TriggerEventBuffer[0]']['Partition'] = group gate = cfg['user']['gate_ns'] cfg['expert']['ClinkFeb[0]']['TrigCtrl[0]'][ 'TrigPulseWidth'] = gate * 0.001 # set bool parameters cfg['expert']['ClinkFeb[0]']['TrigCtrl[0]']['EnableTrig'] = True cfg['expert']['ClinkFeb[0]']['TrigCtrl[0]']['InvCC'] = False cfg['expert']['ClinkFeb[0]']['ClinkTop']['Ch[0]']['DataEn'] = True cfg['expert']['ClinkFeb[0]']['ClinkTop']['Ch[0]']['Blowoff'] = False uart = getattr( getattr(cl, 'ClinkFeb[%d]' % lane).ClinkTop, 'Ch[%d]' % chan).UartPiranha4 cl.ClinkFeb[0].ClinkTop.Ch[0].UartPiranha4.SendEscape() depth = 0 path = 'cl' my_queue = deque( [[path, depth, cl, cfg['expert']]] ) #contains path, dfs depth, rogue hiearchy, and daq configdb dict tree node while (my_queue): path, depth, rogue_node, configdb_node = my_queue.pop() # Replace configdb lane and febch for the physical values if (dict is type(configdb_node)): for i in configdb_node: # Substitute proper pgp lane or feb channel if i == 'ClinkFeb[0]': my_queue.appendleft([ path + "." + i, depth + 1, rogue_node.nodes['ClinkFeb[%d]' % lane], configdb_node[i] ]) elif i == 'Ch[0]': my_queue.appendleft([ path + "." + i, depth + 1, rogue_node.nodes['Ch[%d]' % chan], configdb_node[i] ]) else: try: my_queue.appendleft([ path + "." + i, depth + 1, rogue_node.nodes[i], configdb_node[i] ]) except KeyError: print('Lookup failed for node [{:}] in path [{:}]'. format(i, path)) if ('get' in dir(rogue_node) and 'set' in dir(rogue_node) and path is not 'cl'): # All FIR parameters are stored in configdb as hex strings (I don't know why) if ".FIR." in path: print(path + ", rogue value = " + str(hex(rogue_node.get())) + ", daq config database = " + str(configdb_node)) rogue_node.set(int(str(configdb_node), 16)) else: rogue_node.set(configdb_node) if 'Uart' in path: if 'ROI[0]' in path or 'SAD[0]' in path or 'SAD[1]' in path: # These don't cause the send of a serial command pass else: print('sleeping for {:}'.format(path)) cl_poll(uart) #commands can be sent manually using cl.ClinkFeb0.ClinkTop.Ch0.UartPiranha4._tx.sendString('GCP') # GCP returns configuration summary uart._tx.sendString('gcp') cl_poll(uart) #cl.TimeToolKcu1500.Kcu1500Hsio.TimingRx.XpmMiniWrapper.XpmMini.HwEnable.set(True) cl.TimeToolKcu1500.Kcu1500Hsio.TimingRx.TriggerEventManager.TriggerEventBuffer[ 0].MasterEnable.set(True) # Capture the firmware version to persist in the xtc cfg['firmwareVersion'] = cl.TimeToolKcu1500.AxiPcieCore.AxiVersion.FpgaVersion.get( ) cfg['firmwareBuild'] = cl.TimeToolKcu1500.AxiPcieCore.AxiVersion.BuildStamp.get( ) return json.dumps(cfg)
def ts_config(connect_json,cfgtype,detname,detsegm): cfg = get_config(connect_json,cfgtype,detname,detsegm) connect_info = json.loads(connect_json) # get the list of readout groups that the user has selected # so we only configure those readout_groups = [] connect_info = json.loads(connect_json) for nodes in connect_info['body']['drp'].values(): readout_groups.append(nodes['det_info']['readout']) readout_groups = set(readout_groups) control_info = connect_info['body']['control']['0']['control_info'] xpm_master = control_info['xpm_master'] pv_prefix = control_info['pv_base']+':XPM:'+str(xpm_master)+':PART:' rcfg = cfg.copy() rcfg['user' ] = {} rcfg['expert'] = {} linacMode = cfg['user']['LINAC'] rcfg['user']['LINAC'] = linacMode rcfg['user']['Cu' if linacMode==0 else 'SC'] = {} pvdict = {} # dictionary of epics pv name : value for group in readout_groups: if linacMode == 0: # Cu grp_prefix = 'group'+str(group)+'_eventcode' eventcode = cfg['user']['Cu'][grp_prefix] rcfg['user']['Cu'][grp_prefix] = eventcode pvdict[str(group)+':L0Select' ] = 2 # eventCode pvdict[str(group)+':L0Select_EventCode'] = eventcode pvdict[str(group)+':DstSelect' ] = 1 # DontCare else: # SC grp_prefix = 'group'+str(group) grp = cfg['user']['SC'][grp_prefix] rcfg['user']['SC'][grp_prefix] = grp pvdict[str(group)+':L0Select' ] = grp['trigMode'] pvdict[str(group)+':L0Select_FixedRate'] = grp['fixed']['rate'] pvdict[str(group)+':L0Select_ACRate' ] = grp['ac']['rate'] pvdict[str(group)+':L0Select_EventCode'] = 0 # not an option pvdict[str(group)+':L0Select_Sequence' ] = grp['seq']['mode'] pvdict[str(group)+':DstSelect' ] = grp['destination']['select'] # convert ac.ts0 through ac.ts5 to L0Select_ACTimeslot bitmask tsmask = 0 for tsnum in range(6): tsval = grp['ac']['ts'+str(tsnum)] tsmask |= 1<<tsval pvdict[str(group)+':L0Select_ACTimeslot'] = tsmask # L0Select_SeqBit is one var used by all of seq.(burst/fixed/local) if grp['seq']['mode']==15: # burst seqbit = grp['seq']['burst']['mode'] elif grp['seq']['mode']==16: # fixed rate seqbit = grp['seq']['fixed']['rate'] elif grp['seq']['mode']==17: # local seqbit = grp['seq']['local']['rate'] else: raise ValueError('Illegal value for trigger sequence mode') pvdict[str(group)+':L0Select_SeqBit'] = seqbit # DstSelect_Mask should come from destination.dest0 through dest15 dstmask = 0 for dstnum in range(16): dstval = grp['destination']['dest'+str(dstnum)] if dstval: dstmask |= 1<<dstnum pvdict[str(group)+':DstSelect_Mask'] = dstmask grp_prefix = 'group'+str(group) grp = cfg['expert'][grp_prefix] rcfg['expert'][grp_prefix] = grp # 4 InhEnable/InhInterval/InhLimit for inhnum in range(4): pvdict[str(group)+':InhInterval'+str(inhnum)] = grp['inhibit'+str(inhnum)]['interval'] pvdict[str(group)+':InhLimit'+str(inhnum)] = grp['inhibit'+str(inhnum)]['limit'] pvdict[str(group)+':InhEnable'+str(inhnum)] = grp['inhibit'+str(inhnum)]['enable'] names = list(pvdict.keys()) values = list(pvdict.values()) names = [pv_prefix+n for n in names] # program the values ctxt = Context('pva') ctxt.put(names,values) # Capture firmware version for persistence in xtc pv_prefix = control_info['pv_base']+':XPM:'+str(xpm_master)+':' #rcfg['firmwareVersion'] = ctxt.get(pv_prefix+'FwVersion').raw.value rcfg['firmwareBuild' ] = ctxt.get(pv_prefix+'FwBuild').raw.value ctxt.close() return json.dumps(rcfg)
def hsd_config(connect_str, prefix, cfgtype, detname, detsegm, group): global partitionDelay global epics_prefix global ocfg epics_prefix = prefix cfg = get_config(connect_str, cfgtype, detname, detsegm) # fetch the current configuration for defaults not specified in the configuration ctxt = Context('pva') values = ctxt.get(epics_prefix + ':CONFIG') # fetch the xpm delay partitionDelay = ctxt.get(epics_prefix + ':MONTIMING').msgdelayset print('partitionDelay {:}'.format(partitionDelay)) # # Validate user raw values # raw = cfg['user']['raw'] raw_start = int((raw['start_ns'] * 1300 / 7000 - partitionDelay * 200) * 160 / 200) # in "160MHz"(*13/14) clks # raw_start register is 14 bits if raw_start < 0: print('partitionDelay {:} raw_start_ns {:} raw_start {:}'.format( partitionDelay, raw['start_ns'], raw_start)) raise ValueError('raw_start is too small by {:} ns'.format( -raw_start / 0.16 * 14. / 13)) if raw_start > 0x3fff: print('partitionDelay {:} raw_start_ns {:} raw_start {:}'.format( partitionDelay, raw['start_ns'], raw_start)) raise ValueError('start_ns is too large by {:} ns'.format( (raw_start - 0x3fff) / 0.16 * 14. / 13)) raw_gate = int(raw['gate_ns'] * 0.160 * 13 / 14) # in "160" MHz clks raw_nsamples = raw_gate * 40 # raw_gate register is 14 bits if raw_gate < 0: raise ValueError('raw_gate computes to < 0') if raw_gate > 4000: raise ValueError('raw_gate computes to > 4000; raw_nsamples > 160000') # # Validate user fex values # fex = cfg['user']['fex'] fex_start = int((fex['start_ns'] * 1300 / 7000 - partitionDelay * 200) * 160 / 200) # in "160MHz"(*13/14) clks if fex_start < 0: print('partitionDelay {:} fex_start_ns {:} fex_start {:}'.format( partitionDelay, fex['start_ns'], fex_start)) raise ValueError('fex_start computes to < 0') fex_gate = int(fex['gate_ns'] * 0.160 * 13 / 14) # in "160" MHz clks fex_nsamples = fex_gate * 40 if fex_gate < 0: raise ValueError('fex_gate computes to < 0') # Place no constraint on upper bound. Assumes sparsification will reduce to < 160000 recorded samples # hsd_thr_ilv_native_fine firmware expects xpre,xpost in # of super samples (4 samples) fex_xpre = int((fex['xpre'] + 3) / 4) fex_xpost = int((fex['xpost'] + 3) / 4) # overwrite expert fields from user input expert = cfg['expert'] expert['readoutGroup'] = group expert['enable'] = 1 expert['raw_start'] = raw_start expert['raw_gate'] = raw_gate expert['raw_prescale'] = raw['prescale'] expert['fex_start'] = fex_start expert['fex_gate'] = fex_gate expert['fex_xpre'] = fex_xpre expert['fex_xpost'] = fex_xpost expert['fex_ymin'] = fex['ymin'] expert['fex_ymax'] = fex['ymax'] expert['fex_prescale'] = fex['prescale'] # program the values apply_config(ctxt, cfg) fwver = ctxt.get(epics_prefix + ':FWVERSION').value fwbld = ctxt.get(epics_prefix + ':FWBUILD').value cfg['firmwareVersion'] = fwver cfg['firmwareBuild'] = fwbld print(f'fwver: {fwver}') print(f'fwbld: {fwbld}') ctxt.close() ocfg = cfg return json.dumps(cfg)
def epixquad_config(base, connect_str, cfgtype, detname, detsegm, rog): global ocfg global group global segids group = rog _checkADCs() # # Retrieve the full configuration from the configDB # cfg = get_config(connect_str, cfgtype, detname, detsegm) ocfg = cfg # Translate user settings to the expert fields user_to_expert(base, cfg, full=True) # Apply the expert settings to the device config_expert(base, cfg) pbase = base['pci'] pbase.StartRun() # Add some counter resets here reset_counters(base) # Capture the firmware version to persist in the xtc cbase = base['cam'] firmwareVersion = cbase.AxiVersion.FpgaVersion.get() ocfg = cfg # # Create the segment configurations from parameters required for analysis # trbit = [ cfg['expert']['EpixQuad'][f'Epix10kaSaci{i}']['trbit'] for i in range(16) ] topname = cfg['detName:RO'].split('_') scfg = {} segids = {} # Rename the complete config detector scfg[0] = cfg.copy() scfg[0]['detName:RO'] = topname[0] + 'hw_' + topname[1] a = np.array(cfg['user']['pixel_map'], dtype=np.uint8) pixelConfigMap = np.reshape(a, (16, 178, 192)) for seg in range(4): # Construct the ID carrierId = [ cbase.SystemRegs.CarrierIdLow[seg].get(), cbase.SystemRegs.CarrierIdHigh[seg].get() ] digitalId = [0, 0] analogId = [0, 0] id = '%010d-%010d-%010d-%010d-%010d-%010d-%010d' % ( firmwareVersion, carrierId[0], carrierId[1], digitalId[0], digitalId[1], analogId[0], analogId[1]) segids[seg] = id top = cdict() top.setAlg('config', [2, 0, 0]) top.setInfo(detType='epix10ka', detName=topname[0], detSegm=seg + 4 * int(topname[1]), detId=id, doc='No comment') top.set('asicPixelConfig', pixelConfigMap[4 * seg:4 * seg + 4, :176].tolist(), 'UINT8') # only the rows which have readable pixels top.set('trbit', trbit[4 * seg:4 * seg + 4], 'UINT8') scfg[seg + 1] = top.typed_json() result = [] for i in seglist: print('json seg {} detname {}'.format(i, scfg[i]['detName:RO'])) result.append(json.dumps(scfg[i])) return result
def opal_config(cl, connect_str, cfgtype, detname, detsegm, group): cfg = get_config(connect_str, cfgtype, detname, detsegm) lane = 0 chan = 0 if (cl.ClinkPcie.Hsio.PgpMon[0].RxRemLinkReady.get() != 1): raise ValueError(f'PGP Link is down') # drain any data in the event pipeline getattr(cl.ClinkPcie.Application, 'AppLane[%d]' % lane).EventBuilder.Blowoff.set(True) getattr(getattr(cl, 'ClinkFeb[%d]' % lane).ClinkTop, 'Ch[%d]' % chan).Blowoff.set(True) # overwrite the low-level configuration parameters with calculations from the user configuration partitionDelay = getattr( cl.ClinkPcie.Hsio.TimingRx.TriggerEventManager.XpmMessageAligner, 'PartitionDelay[%d]' % group).get() rawStart = cfg['user']['start_ns'] triggerDelay = int(rawStart * 1300 / 7000 - partitionDelay * 200) print('partitionDelay {:} rawStart {:} triggerDelay {:}'.format( partitionDelay, rawStart, triggerDelay)) if triggerDelay < 0: print('partitionDelay {:} rawStart {:} triggerDelay {:}'.format( partitionDelay, rawStart, triggerDelay)) raise ValueError('triggerDelay computes to < 0') cfg['expert']['ClinkPcie']['Hsio']['TimingRx']['TriggerEventManager'][ 'TriggerEventBuffer[0]']['TriggerDelay'] = triggerDelay cfg['expert']['ClinkPcie']['Hsio']['TimingRx']['TriggerEventManager'][ 'TriggerEventBuffer[0]']['Partition'] = group gate = cfg['user']['gate_ns'] cfg['expert']['ClinkFeb[0]']['TrigCtrl[0]'][ 'TrigPulseWidth'] = gate * 0.001 cfg['expert']['ClinkFeb[0]']['ClinkTop']['Ch[0]']['UartOpal1000'][ 'BL'] = cfg['user']['black_level'] cfg['expert']['ClinkFeb[0]']['ClinkTop']['Ch[0]']['UartOpal1000'][ 'VBIN'] = cfg['user']['vertical_bin'] # set bool parameters cfg['expert']['ClinkFeb[0]']['TrigCtrl[0]']['EnableTrig'] = True cfg['expert']['ClinkFeb[0]']['TrigCtrl[0]']['InvCC'] = False cfg['expert']['ClinkFeb[0]']['ClinkTop']['Ch[0]']['DataEn'] = True cfg['expert']['ClinkFeb[0]']['ClinkTop']['Ch[0]']['Blowoff'] = False # trigger polarity inversion for firmware version uart = getattr( getattr(cl, 'ClinkFeb[%d]' % lane).ClinkTop, 'Ch[%d]' % chan).UartOpal1000 try: v = uart.BS.get() uart.BS.set(str(int(v) + 1)) except: uart.BS.set('0') time.sleep(0.10) fwver = uart._rx._last.split(';') if len(fwver) > 2: major, minor = fwver[2].split('.')[:2] if int(major) < 1 or int(minor) < 20: print('Normal polarity') cfg['expert']['ClinkFeb[0]']['ClinkTop']['Ch[0]']['UartOpal1000'][ 'CCE[1]'] = 0 else: print('Inverted polarity') cfg['expert']['ClinkFeb[0]']['ClinkTop']['Ch[0]']['UartOpal1000'][ 'CCE[1]'] = 1 # invert polarity depth = 0 path = 'cl' my_queue = deque( [[path, depth, cl, cfg['expert']]] ) #contains path, dfs depth, rogue hiearchy, and daq configdb dict tree node while (my_queue): path, depth, rogue_node, configdb_node = my_queue.pop() # Replace configdb lane and febch for the physical values if (dict is type(configdb_node)): for i in configdb_node: # Substitute proper pgp lane or feb channel if i == 'ClinkFeb[0]': my_queue.appendleft([ path + "." + i, depth + 1, rogue_node.nodes['ClinkFeb[%d]' % lane], configdb_node[i] ]) elif i == 'Ch[0]': my_queue.appendleft([ path + "." + i, depth + 1, rogue_node.nodes['Ch[%d]' % chan], configdb_node[i] ]) else: try: my_queue.appendleft([ path + "." + i, depth + 1, rogue_node.nodes[i], configdb_node[i] ]) except KeyError: print('Lookup failed for node [{:}] in path [{:}]'. format(i, path)) # Apply if ('get' in dir(rogue_node) and 'set' in dir(rogue_node) and path is not 'cl'): rogue_node.set(configdb_node) cl.ClinkPcie.Hsio.TimingRx.XpmMiniWrapper.XpmMini.HwEnable.set(True) cl.ClinkPcie.Hsio.TimingRx.TriggerEventManager.TriggerEventBuffer[ 0].MasterEnable.set(True) getattr(cl.ClinkPcie.Application, 'AppLane[%d]' % lane).EventBuilder.Blowoff.set(False) # Capture the firmware version to persist in the xtc cfg['firmwareVersion'] = cl.ClinkPcie.AxiPcieCore.AxiVersion.FpgaVersion.get( ) cfg['firmwareBuild'] = cl.ClinkPcie.AxiPcieCore.AxiVersion.BuildStamp.get() cl.StartRun() return json.dumps(cfg)
def epixquad_config(base, connect_str, cfgtype, detname, detsegm, rog): global ocfg global group group = rog # # Retrieve the full configuration from the configDB # cfg = get_config(connect_str, cfgtype, detname, detsegm) ocfg = cfg # Translate user settings to the expert fields user_to_expert(base, cfg, full=True) # Apply the expert settings to the device config_expert(base, cfg) pbase = base['pci'] #pbase.DevPcie.Hsio.TimingRx.XpmMiniWrapper.XpmMini.HwEnable.set(True) #getattr(pbase.DevPcie.Hsio.TimingRx.TriggerEventManager,f'TriggerEventBuffer[{lane}]').MasterEnable.set(True) #getattr(pbase.DevPcie.Application,'AppLane[%d]'%lane).EventBuilder.Blowoff.set(False) pbase.StartRun() # Capture the firmware version to persist in the xtc cbase = base['cam'] firmwareVersion = cbase.AxiVersion.FpgaVersion.get() #cfg['firmwareVersion:RO'] = cbase.AxiVersion.FpgaVersion.get() #cfg['firmwareBuild:RO' ] = cbase.AxiVersion.BuildStamp.get() # print('--Configuring AsicMatrix for injection--') # cbase.SetAsicMatrixTest() ocfg = cfg #return [json.dumps(cfg)] # # Create the segment configurations from parameters required for analysis # trbit = [ cfg['expert']['EpixQuad'][f'Epix10kaSaci[{i}]']['trbit'] for i in range(16) ] topname = cfg['detName:RO'].split('_') scfg = {} # Rename the complete config detector scfg[0] = cfg.copy() scfg[0]['detName:RO'] = topname[0] + 'hw_' + topname[1] a = np.array(cfg['user']['pixel_map'], dtype=np.uint8) pixelConfigMap = np.reshape(a, (16, 178, 192)) for seg in range(4): # Construct the ID carrierId = [ cbase.SystemRegs.CarrierIdLow[seg].get(), cbase.SystemRegs.CarrierIdHigh[seg].get() ] digitalId = [0, 0] analogId = [0, 0] id = '%010d-%010d-%010d-%010d-%010d-%010d-%010d' % ( firmwareVersion, carrierId[0], carrierId[1], digitalId[0], digitalId[1], analogId[0], analogId[1]) top = cdict() top.setAlg('config', [2, 0, 0]) top.setInfo(detType='epix', detName=topname[0], detSegm=seg + 4 * int(topname[1]), detId=id, doc='No comment') top.set('asicPixelConfig', pixelConfigMap[4 * seg:4 * seg + 4, :176].tolist(), 'UINT8') # only the rows which have readable pixels top.set('trbit', trbit[4 * seg:4 * seg + 4], 'UINT8') scfg[seg + 1] = top.typed_json() result = [] for i in range(5): print('json seg {} detname {}'.format(i, scfg[i]['detName:RO'])) result.append(json.dumps(scfg[i])) return result
def hsd_config(connect_str, epics_prefix, cfgtype, detname, detsegm, group): cfg = get_config(connect_str, cfgtype, detname, detsegm) # fetch the current configuration for defaults not specified in the configuration ctxt = Context('pva') values = ctxt.get(epics_prefix + ':CONFIG') # fetch the xpm delay partitionDelay = ctxt.get(epics_prefix + ':MONTIMING').msgdelayset print('partitionDelay {:}'.format(partitionDelay)) # # Validate user raw values # raw = cfg['user']['raw'] raw_start = (raw['start_ns'] * 1300 / 7000 - partitionDelay * 200) * 160 / 200 # in "160MHz"(*13/14) clks if raw_start < 0: print('partitionDelay {:} raw_start_ns {:} raw_start {:}'.format( partitionDelay, raw['start_ns'], raw_start)) raise ValueError('raw_start computes to < 0') raw_gate = int(raw['gate_ns'] * 0.160 * 13 / 14) # in "160" MHz clks raw_nsamples = raw_gate * 40 if raw_gate < 0: raise ValueError('raw_gate computes to < 0') if raw_gate > 4000: raise ValueError('raw_gate computes to > 4000; raw_nsamples > 160000') # # Validate user fex values # fex = cfg['user']['fex'] fex_start = int((fex['start_ns'] * 1300 / 7000 - partitionDelay * 200) * 160 / 200) # in "160MHz"(*13/14) clks if fex_start < 0: print('partitionDelay {:} fex_start_ns {:} fex_start {:}'.format( partitionDelay, fex['start_ns'], fex_start)) raise ValueError('fex_start computes to < 0') fex_gate = int(fex['gate_ns'] * 0.160 * 13 / 14) # in "160" MHz clks fex_nsamples = fex_gate * 40 if fex_gate < 0: raise ValueError('fex_gate computes to < 0') # Place no constraint on upper bound. Assumes sparsification will reduce to < 160000 recorded samples # hsd_thr_ilv_native_fine firmware expects xpre,xpost in # of super samples (4 samples) fex_xpre = int((fex['xpre'] + 3) / 4) fex_xpost = int((fex['xpost'] + 3) / 4) # overwrite expert fields from user input expert = cfg['expert'] expert['readoutGroup'] = group expert['enable'] = 1 expert['raw_start'] = raw_start expert['raw_gate'] = raw_gate expert['raw_prescale'] = raw['prescale'] expert['fex_start'] = fex_start expert['fex_gate'] = fex_gate expert['fex_xpre'] = fex_xpre expert['fex_xpost'] = fex_xpost expert['fex_prescale'] = fex['prescale'] # program the values print(epics_prefix) ctxt.put(epics_prefix + ':READY', 0, wait=True) ctxt.put(epics_prefix + ':CONFIG', expert, wait=True) # the completion of the "put" guarantees that all of the above # have completed (although in no particular order) complete = False for i in range(100): complete = ctxt.get(epics_prefix + ':READY') != 0 if complete: break print('hsd config wait for complete', i) time.sleep(0.1) if complete: print('hsd config complete') else: raise Exception('timed out waiting for hsd configure') cfg['firmwareVersion'] = ctxt.get(epics_prefix + ':FWVERSION').raw.value cfg['firmwareBuild'] = ctxt.get(epics_prefix + ':FWBUILD').raw.value ctxt.close() return json.dumps(cfg)
def epixhr2x2_config(base, connect_str, cfgtype, detname, detsegm, rog): global ocfg global group global segids group = rog # _checkADCs() # # Retrieve the full configuration from the configDB # cfg = get_config(connect_str, cfgtype, detname, detsegm) ocfg = cfg # Translate user settings to the expert fields writePixelMap = user_to_expert(base, cfg, full=True) # Apply the expert settings to the device pbase = base['pci'] pbase.StopRun() time.sleep(0.01) config_expert(base, cfg, writePixelMap) time.sleep(0.01) pbase.StartRun() # Add some counter resets here reset_counters(base) # Enable triggers to continue monitoring epixhr2x2_internal_trigger(base) # Capture the firmware version to persist in the xtc cbase = base['cam'] firmwareVersion = cbase.Core.AxiVersion.FpgaVersion.get() ocfg = cfg # # Create the segment configurations from parameters required for analysis # trbit = [ cfg['expert']['EpixHR'][f'Hr10kTAsic{i}']['trbit'] for i in range(4) ] topname = cfg['detName:RO'].split('_') scfg = {} segids = {} # Rename the complete config detector scfg[0] = cfg.copy() scfg[0]['detName:RO'] = topname[0] + 'hw_' + topname[1] # User pixel map is assumed to be 288x384 in standard element orientation gain_mode = cfg['user']['gain_mode'] if gain_mode == 5: pixelConfigUsr = np.array(cfg['user']['pixel_map'], dtype=np.uint8) else: mapv, trbit = gain_mode_map(gain_mode) pixelConfigUsr = np.zeros( (2 * elemRowsD, 2 * elemCols), dtype=np.uint8) + mapv pixelConfigMap = user_to_rogue(pixelConfigUsr) for seg in range(1): # Construct the ID # carrierId = [ cbase.SystemRegs.CarrierIdLow [seg].get(), # cbase.SystemRegs.CarrierIdHigh[seg].get() ] carrierId = [0, 0] digitalId = [0, 0] analogId = [0, 0] id = '%010d-%010d-%010d-%010d-%010d-%010d-%010d' % ( firmwareVersion, carrierId[0], carrierId[1], digitalId[0], digitalId[1], analogId[0], analogId[1]) segids[seg] = id top = cdict() top.setAlg('config', [2, 0, 0]) top.setInfo(detType='epixhr2x2', detName=topname[0], detSegm=seg + int(topname[1]), detId=id, doc='No comment') top.set('asicPixelConfig', pixelConfigUsr) top.set('trbit', [trbit for i in range(4)], 'UINT8') scfg[seg + 1] = top.typed_json() result = [] for i in seglist: logging.debug('json seg {} detname {}'.format(i, scfg[i]['detName:RO'])) result.append(json.dumps(scfg[i])) return result