def test_epicssignal_set(put_complete): sim_pv = EpicsSignal(write_pv='XF:31IDA-OP{Tbl-Ax:X1}Mtr.VAL', read_pv='XF:31IDA-OP{Tbl-Ax:X1}Mtr.RBV', put_complete=put_complete) sim_pv.wait_for_connection() logging.getLogger('ophyd.signal').setLevel(logging.DEBUG) logging.getLogger('ophyd.utils.epics_pvs').setLevel(logging.DEBUG) print('tolerance=', sim_pv.tolerance) assert sim_pv.tolerance is not None start_pos = sim_pv.get() # move to +0.2 and check the status object target = sim_pv.get() + 0.2 st = sim_pv.set(target, timeout=1, settle_time=0.001) wait(st, timeout=5) assert st.done assert st.success print('status 1', st) assert abs(target - sim_pv.get()) < 0.05 # move back to -0.2, forcing a timeout with a low value target = sim_pv.get() - 0.2 st = sim_pv.set(target, timeout=1e-6) time.sleep(0.1) print('status 2', st) assert st.done assert not st.success # keep the axis in position st = sim_pv.set(start_pos) wait(st, timeout=5)
def test_epicssignal_set(cleanup, motor, put_complete): sim_pv = EpicsSignal(write_pv=motor.user_setpoint.pvname, read_pv=motor.user_readback.pvname, put_complete=put_complete) cleanup.add(sim_pv) sim_pv.wait_for_connection() logging.getLogger('ophyd.signal').setLevel(logging.DEBUG) logging.getLogger('ophyd.utils.epics_pvs').setLevel(logging.DEBUG) print('tolerance=', sim_pv.tolerance) assert sim_pv.tolerance is not None start_pos = sim_pv.get() # move to +0.2 and check the status object target = sim_pv.get() + 0.2 st = sim_pv.set(target, timeout=1, settle_time=0.001) wait(st, timeout=5) assert st.done assert st.success print('status 1', st) assert abs(target - sim_pv.get()) < 0.05 # move back to -0.2, forcing a timeout with a low value target = sim_pv.get() - 0.2 st = sim_pv.set(target, timeout=1e-6) time.sleep(0.5) print('status 2', st) assert st.done assert not st.success # keep the axis in position st = sim_pv.set(start_pos) wait(st, timeout=5)
def test_epicssignal_set(put_complete): sim_pv = EpicsSignal(write_pv='XF:31IDA-OP{Tbl-Ax:X1}Mtr.VAL', read_pv='XF:31IDA-OP{Tbl-Ax:X1}Mtr.RBV', put_complete=put_complete) sim_pv.wait_for_connection() logging.getLogger('ophyd.signal').setLevel(logging.DEBUG) logging.getLogger('ophyd.utils.epics_pvs').setLevel(logging.DEBUG) print('tolerance=', sim_pv.tolerance) assert sim_pv.tolerance is not None start_pos = sim_pv.get() # move to +0.2 and check the status object target = sim_pv.get() + 0.2 st = sim_pv.set(target, timeout=1, settle_time=0.001) wait(st) assert st.done assert st.success print('status 1', st) assert abs(target - sim_pv.get()) < 0.05 # move back to -0.2, forcing a timeout with a low value target = sim_pv.get() - 0.2 st = sim_pv.set(target, timeout=1e-6) time.sleep(0.1) print('status 2', st) assert st.done assert not st.success # keep the axis in position st = sim_pv.set(start_pos) wait(st)
def matlabPV_FB(feedbackvalue): #get and put timedelay signal matPV = EpicsSignal('LAS:FS4:VIT:matlab:04') org_matPV = matPV.get() #the matlab PV value before FB fbvalns = feedbackvalue * 1e+9 #feedback value in ns fbinput = org_matPV + fbvalns #relative to absolute value matPV.put(fbinput) return
def get_ttall(): #get timetool related signal ttall = EpicsSignal('XCS:TIMETOOL:TTALL') ttdata = ttall.get() current_tt = ttdata[1, ] ttamp = ttdata[2, ] ipm4val = ttdata[3, ] ttfwhm = ttdata[5, ] return current_tt, ttamp, ipm4val, ttfwhm
def test_no_connection(cleanup, signal_test_ioc): sig = EpicsSignal('does_not_connect') cleanup.add(sig) with pytest.raises(TimeoutError): sig.wait_for_connection() sig = EpicsSignal('does_not_connect') cleanup.add(sig) with pytest.raises(TimeoutError): sig.put(0.0) with pytest.raises(TimeoutError): sig.get() sig = EpicsSignal(signal_test_ioc.pvs['read_only'], write_pv='does_not_connect') cleanup.add(sig) with pytest.raises(TimeoutError): sig.wait_for_connection()
class TimingChannel(object): def __init__(self, setpoint_PV, readback_PV, name): self.control_PV = EpicsSignal(setpoint_PV) # DG/Vitara PV self.storage_PV = EpicsSignal(readback_PV) # Notepad PV self.name = name def save_t0(self, val=None): """ Set the t0 value directly, or save the current value as t0. """ if not val: # Take current value to be t0 if not provided val = self.control_PV.get() self.storage_PV.put(val) # Save t0 value def restore_t0(self): """ Restore the t0 value from the current saved value for t0. """ val = self.storage_PV.get() self.control_PV.put(val) # write t0 value def mvr(self, relval): """ Move the control PV relative to it's current value. """ currval = self.control_PV.get() self.control_PV.put(currval - relval) def mv(self, val): t0 = self.storage_PV.get() self.control_PV.put(t0 - val) def get_delay(self, verbose=False): delay = self.control_PV.get() - self.storage_PV.get() if delay > 0: print("X-rays arrive {} s before the optical laser".format( abs(delay))) elif delay < 0: print("X-rays arrive {} s after the optical laser".format( abs(delay))) else: # delay is 0 print("X-rays arrive at the same time as the optical laser") if verbose: control_data = (self.name, self.control_PV.pvname, self.control_PV.get()) storage_data = (self.name, self.storage_PV.pvname, self.storage_PV.get()) print("{} Control PV: {}, Control Value: {}".format(*control_data)) print("{} Storage PV: {}, Storage Value: {}".format(*storage_data))
def tt_rough_FB(ttamp_th=0.02, ipm4_th=500, tt_window=0.05): fbvalue = 0 # for drift record while (1): tenshots_tt = np.zeros([ 1, ]) dlen = 0 while (dlen < 61): #ttcomm = Popen("caget XPP:TIMETOOL:TTALL",shell = True, stdout=PIPE) #ttdata = (ttcomm.communicate()[0]).decode() ttall = EpicsSignal('XCS:TIMETOOL:TTALL') ttdata = ttall.get() current_tt = ttdata[1, ] ttamp = ttdata[2, ] ipm4val = ttdata[3, ] ttfwhm = ttdata[5, ] #current_tt = float((ttdata.split(" "))[3]) #ttamp = float((ttdata.split(" "))[4]) #ipm2val = float((ttdata.split(" "))[5]) #ttfwhm = float((ttdata.split(" "))[7]) if (dlen % 10 == 0): #print("tt_value",current_tt,"ttamp",ttamp,"ipm4",ipm4val) print("tt_value:%0.3f" % current_tt + " ttamp:%0.3f " % ttamp + " ipm4:%d" % ipm4val) if (ttamp > ttamp_th) and (ipm4val > ipm4_th) and ( ttfwhm < 130 ) and (ttfwhm > 30) and ( current_tt != tenshots_tt[-1, ] ): # for filtering the last one is for when DAQ is stopping tenshots_tt = np.insert(tenshots_tt, dlen, current_tt) dlen = np.shape(tenshots_tt)[0] time.sleep(0.01) tenshots_tt = np.delete(tenshots_tt, 0) ave_tt = np.mean(tenshots_tt) print("Moving average of timetool value:", ave_tt) if np.abs(ave_tt) > tt_window: ave_tt_second = -(ave_tt * 1e-12) lxt.mvr(ave_tt_second) print("feedback %f ps" % ave_tt) fbvalue = ave_tt + fbvalue #drift_log(str(fbvalue)) return
def test_epicssignal_waveform(cleanup, signal_test_ioc): called = False def update_cb(value=None, **kwargs): nonlocal called assert len(value) > 1 called = True signal = EpicsSignal(signal_test_ioc.pvs['waveform'], string=True) cleanup.add(signal) signal.wait_for_connection() sub = signal.subscribe(update_cb, event_type=signal.SUB_VALUE) assert len(signal.get()) > 1 # force the current thread to allow other threads to run to service # subscription time.sleep(0.2) assert called signal.unsubscribe(sub)
class User(): def __init__(self): #switch to trigger instead of full evr self._sync_markers = { 0.5: 0, 1: 1, 5: 2, 10: 3, 30: 4, 60: 5, 120: 6, 360: 7 } self.trigger_mag = Trigger('XCS:R42:EVR:01:TRIG4', name='trigger_mag') self.trigger_pp = Trigger('XCS:USR:EVR:TRIG1', name='trigger_pp') #self.nemptyshots = actions(0, name='nemptyshots') #self.isfire = actions(False, name='isfire') #self.emptyshotspacing = actions(0, name='emptyshotspacing') #self.nshots = actions(0, name='nshots') #self.shotspacing = actions(0, name='shotspacing') #with safe_load('Pirani and Cold Cathode Gauges'): # self.mag_pirani = BaseGauge('XCS:USR:GPI:01', name='mag_pirani') # self.mag_cc = BaseGauge('XCS:USR:GCC:01', name='mag_cc') self.sample_temp = LakeShoreChannel('XCS:USR:TCT:02', name='A') self.mag_temp = LakeShoreChannel('XCS:USR:TCT:02', name='B') self.ttl_high = 2.0 self.ttl_low = 0.8 self._ready_sig = EpicsSignal('XCS:USR:ai1:0', name='User Analog Input channel 0', kind='omitted') self.i0_threshold = 4000 # default threshold is 0 self.i0_avg = AvgSignal(ipm4.wave8.isum, 30, name='ipm4_sum_avg') self.i0_mag_retry = 10 self._gdet_threshold_pv = EpicsSignal('XCS:VARS:J78:GDET_THRES', kind='normal') #self.gdet_avg_count = 30 #self.gdet_mag_retry = 10 #self.gdet = GasDetector('GDET:FEE1', name='gas detector') #self._bykik_pv = Cpt(EpicsSignal('IOC:IN20:EV01:BYKIK_ABTACT', kind = 'normal', string=True, doc='BYKIK: Abort Active') self._req_burst_rate = 'Full' self._test_burst_rate = EpicsSignal('PATT:SYS0:1:TESTBURSTRATE', name='test_burst_rate', kind='normal') self._mps_burst_rate = EpicsSignal('PATT:SYS0:1:MPSBURSTRATE', name='mps_burst_rate') # number of seconds to pause between empty and magnet self.pause_time = 2. self._min_empty_delay = 4 self._beam_owner = EpicsSignal('ECS:SYS0:0:BEAM_OWNER_ID', name='beam_owner', kind='normal') self._att = att self.hutch = 'xcs' self._hutch_id = EpicsSignal('ECS:SYS0:4:HUTCH_ID', name='hutch_id', kind='normal') self.aliases = ['BEAM'] self.gainmodes = '' #use lcls.(tab) to find bykik controls @property def machine_burst_rate(self): if self._beam_owner.get() == self._hutch_id.get(): self._mps_burst_rate.get() else: self._test_burst_rate.get() @machine_burst_rate.setter def machine_burst_rate(self, rate): if self._beam_owner.get() == self._hutch_id.get(): self._mps_burst_rate.put(rate) else: self._test_burst_rate.put(rate) def check_burst_rate(self): if self.machine_burst_rate != self._req_burst_rate: print('Machine burst frequency not set to %s! - fixing...' % self._req_burst_rate) if self._beam_owner.get() == self._hutch_id.get(): set_and_wait( self._mps_burst_rate, self._req_burst_rate ) #ophyd set and wait() - ophyd.utils.epics_pvs.set_and_wait else: set_and_wait(self._test_burst_rate, self._req_burst_rate) print('done.') @property def ready_sig(self): return self._ready_sig.get() def seq_wait(self, timeout=0, sleeptime=1.0): print(f'timeout = {timeout}, sleep = {sleeptime}') sleep(sleeptime) start = time.time() print(f'start time: {start}') while seq.play_status.get() != 0: if timeout > 0 and (time.time() - start >= timeout): raise ValueError('Timed out') def _prepare_burst(self, Nshots, Nbursts=1, freq=120, delay=None, burstMode=False): if Nshots == 1: pp.flipflop() elif Nshots > 1: pp.burst() if Nbursts == 1: seq.play_mode.put(0) elif Nbursts > 1: seq.play_mode.put(1) seq.rep_count.put(Nbursts) elif Nbursts < 0: seq.play_mode.put(2) if burstMode: burst = Nshots + 2 else: burst = 0 if not freq == 120: raise (NotImplementedError('Not implemented yet!')) if Nshots == 1: if delay is None: delay = 3 elif delay < 2: raise ValueError( 'Delay between flip flops of less than two is not allowed') ff_seq = [[84, delay, 0, burst], [86, 0, 0, burst], [85, 2, 0, burst]] elif Nshots > 1: if delay is None: delay = 1 elif delay < 1: raise ValueError( 'Delay between bursts of less than one is not allowed') ff_seq = [[84, delay, 0, burst], [86, 0, 0, burst], [86, 1, 0, burst]] for shotNo in range(Nshots): ff_seq.append([85, 1, 0, burst]) if shotNo == Nshots - 2: ff_seq.append([84, 0, 0, burst]) seq.sequence.put_seq(ff_seq) def _prepNonMagShots(self, nshots): #copy code from old pulsepicker.py file in (blinst) and change where needed or xpp experiment self._prepare_burst(nshots, burstMode=True) def _prepSpacedNonMagShots(self, nshots_per_burst, spacing): nshots = 1 burstDelay = spacing - 2 self.prepare_burst(nshots, Nbursts=nshots_per_burst, delay=burstDelay, burstMode=True) def _takeNonMagShots(self): seq.start() def _prepMagShot(self, isfire, delay=1): pp.flipflop() seq.play_mode.put(0) ff_seq = [[84, delay, 0, 3], [86, 0, 0, 0]] if isfire: ff_seq.append([self.trigger_mag.get_eventcode(), 2, 0, 0]) ff_seq.append([85, 0, 0, 0]) else: ff_seq.append([85, 2, 0, 0]) seq.sequence.put_seq(ff_seq) def _takeMagShot(self): seq.start() def _laserOn(self): """ laser on by goose trigger 88 """ os.system('caput XCS:ECS:IOC:01:EC_11:00 88') os.system('caput ECS:SYS0:11:LEN 1') os.system('caput ECS:SYS0:11:PLYCTL 1') def _laserOff(self): """ laser off by goose trigger 89 """ os.system('caput XCS:ECS:IOC:01:EC_11:00 89') os.system('caput ECS:SYS0:11:LEN 1') os.system('caput ECS:SYS0:11:PLYCTL 1') def _laserNormal(self): """ normal on/off mode """ os.system('caput XCS:ECS:IOC:01:EC_11:00 88') os.system('caput ECS:SYS0:11:LEN 7') os.system('caput ECS:SYS0:11:PLYCTL 1') def takeEmptyShots(self, nshots, shotspacing, use_daq=False, record=None): calibcontrols = { 'nshots': ConfigVal(nshots), 'shotspacing': ConfigVal(shotspacing) } if shotspacing > 0: self._prepSpacedNonMagShots(nshots, shotspacing) else: self._prepNonMagShots(nshots) #configure daq if being used if use_daq: daq.record = record daq.configure(events=0, controls=calibcontrols) try: if use_daq: daq.begin(events=nshots, controls=calibcontrols) seq.start() self.seq_wait() if use_daq: daq.wait() except KeyboardInterrupt: seq.stop() finally: if use_daq: daq.record = None daq.disconnect() def takeMagnetShot(self, nemptyshots, emptyshotspacing=0, isfire=False, record=None): calibcontrols = { 'mag_isfire': ConfigVal(isfire), 'mag_trigger_delay': self.trigger_mag.ns_delay, 'mag_trig_width': self.trigger_mag.width, 'mag_trig_eventcode': self.trigger_mag.eventcode, 'nemptyshots': ConfigVal(nemptyshots), 'emptyshotspacing': ConfigVal(emptyshotspacing) } # check the machine burst rate and set to Full rate if not self.check_burst_rate() # disable BYKIK before taking shots lcls.bykik_disable() # check if emptyshotspacing is valid if 0 < emptyshotspacing < self._min_empty_delay: raise ValueError( "When using spacing between empty shots it must be >= %d" % self._min_empty_delay) spacer = "*********************************" print("\n%s\n* Preparing to take magnet shot *\n%s\n" % (spacer, spacer)) if emptyshotspacing > 0: mag_status = "Taking %d shots, with a spacing between each of %d beam pulses, before firing the magnet\n" % ( nemptyshots, emptyshotspacing) else: mag_status = "Taking %d shots before firing the magnet\n" % nemptyshots mag_status += "Magnet pulse eventcode: %d\n" % self.trigger_mag.get_eventcode( ) mag_status += "Magnet pulse trigger delay: %f\n" % self.trigger_mag.get_delay( ) mag_status += "Magnet pulse trigger width: %f\n" % self.trigger_mag.get_width( ) mag_status += "Magnet to be fired: %s\n" % isfire print(mag_status) try: daq.record = record daq.configure(events=0, controls=calibcontrols) # Pre empty shots if nemptyshots > 0: print("\nPreparing sequencer for pre-firing, non-magnet shots") if emptyshotspacing > 0: self._prepSpacedNonMagShots(nemptyshots, emptyshotspacing) else: self._prepNonMagShots(nemptyshots) time.sleep(self.pause_time) daq.begin(events=nemptyshots, controls=calibcontrols) print("\nTaking %d pre-firing, non-magnet shots\n" % nemptyshots) # pause after changing pulse picker mode time.sleep(self.pause_time) self._takeNonMagShots() print('Taking shots') self.seq_wait() print('seq finished') daq.wait() print('daq finished') else: print("\nSkipping prefiring, non-magnet shots\n") # pause after empty shots time.sleep(self.pause_time) print('sleep finished') # Fire the magnet sequence based on isfire flag if isfire: print("Start magnet firing sequence\n") else: print("Start magnet test 'firing' sequence\n") print("\nPreparing sequencer for magnet shot") if emptyshotspacing > 0: self._prepMagShot(isfire, emptyshotspacing) else: self._prepMagShot(isfire) time.sleep(self.pause_time) # pause after changing pulse picker mode time.sleep(self.pause_time) #checking ipm4?? num_tries = 0 i0_good = False while num_tries < self.i0_mag_retry: i0_val = self.i0_avg.get() if i0_val < self.i0_threshold: print( "\nNot firing magnet due to low beam current (ipm4): %.3f \n" % (i0_val)) backoff_time = 2**num_tries print("Sleeping for %d seconds...\n" % backoff_time) time.sleep(backoff_time) num_tries += 1 else: #ipm4 is good - fire! i0_good = True print("\nInitial intensity(ipm4) looks good: %.3f\n" % i0_val) break if not i0_good: print( "Max number of i0 checks (%d) exceeded! - Abort shot attempt.\n" % self.i0_mag_retry) return False # take the magnet shot daq.begin(events=1, controls=calibcontrols) print("\nTaking magnet shot\n") self._takeMagShot() self.seq_wait() daq.wait() #pause after magnet shots time.sleep(self.pause_time) #post empty shots if nemptyshots > 0: print( "\nPreparing sequencer for post-firing, non-magnet shots") if emptyshotspacing > 0: self._prepSpacedNonMagShots(nemptyshots, emptyshotspacing) else: self._prepNonMagShots(nemptyshots) time.sleep(self.pause_time) daq.begin(events=nemptyshots, controls=calibcontrols) print("\nTaking %d post-firing, non-magnet shots\n" % nemptyshots) # pause after changing pulse picker mode time.sleep(self.pause_time) self._takeNonMagShots() self.seq_wait() daq.wait() else: print("\nSkipping post-firing, non-magnet shots\n") return True except KeyboardInterrupt: seq.stop() daq.stop() return False finally: daq.record = None daq.disconnect() lcls.bykik_enable() def takeMagnetShotMulti(self, nemptyshots, emptyshotspacing=0, isfire=False, record=None, ignore_ready=False): """ Takes magnet shots in a continous fashion waiting for a ready signal from the magnet controller """ latch = False nmagshots = 0 shotgood = True spacer = '##############################' try: while shotgood: if not latch and (self.ready_sig > self.ttl_high or ignore_ready): i0_val = self.i0_avg.get() if i0_val < self.i0_threshold: print( "\nNot firing magnet due to low beam current (ipm4): %.3f \n" % (i0_val)) backoff_time = 1 print("Sleeping for %d second...\n" % backoff_time) time.sleep(backoff_time) continue latch = True print("\n%s\nStarting shot %d\n%s\n" % (spacer, nmagshots, spacer)) start_time = time.time() shotgood = self.takeMagnetShot(nemptyshots, emptyshotspacing, isfire, record) stop_time = time.time() print("\n%s\nCompleted shot %d in %.2f s\n%s\n" % (spacer, nmagshots, (stop_time - start_time), spacer)) nmagshots += 1 if latch and (self.ready_sig < self.ttl_low or ignore_ready): latch = False time.sleep(0.25) except KeyboardInterrupt: print('\nExiting...\n') finally: print('Took %d total magnet shots\n' % nmagshots) def takeRun(self, nEvents, record=None, use_l3t=False): daq.configure(events=120, record=record, use_l3t=use_l3t) daq.begin(events=nEvents) daq.wait() daq.end_run() def ascan(self, motor, start, end, nsteps, nEvents, record=None, use_l3t=False): self.cleanup_RE() currPos = motor.wm() daq.configure(nEvents, record=record, controls=[motor], use_l3t=use_l3t) try: RE(scan([daq], motor, start, end, nsteps)) except Exception: logger.debug('RE Exit', exc_info=True) finally: self.cleanup_RE() motor.mv(currPos) def pv_ascan(self, signal, start, end, nsteps, nEvents, record=None, use_l3t=False): self.cleanup_RE() currPos = signal.get() daq.configure(nEvents, record=record, controls=[signal], use_l3t=use_l3t) try: RE(scan([daq], signal, start, end, nsteps)) except Exception: logger.debug('RE Exit', exc_info=True) finally: self.cleanup_RE() signal.put(currPos) def listscan(self, motor, posList, nEvents, record=None, use_l3t=False): self.cleanup_RE() currPos = motor.wm() daq.configure(nEvents, record=record, controls=[motor], use_l3t=use_l3t) try: RE(list_scan([daq], motor, posList)) except Exception: logger.debug('RE Exit', exc_info=True) finally: self.cleanup_RE() motor.mv(currPos) def list3scan(self, m1, p1, m2, p2, m3, p3, nEvents, record=None, use_l3t=False): self.cleanup_RE() currPos1 = m1.wm() currPos2 = m2.wm() currPos3 = m3.wm() daq.configure(nEvents, record=record, controls=[m1, m2, m3], use_l3t=use_l3t) try: RE(list_scan([daq], m1, p1, m2, p2, m3, p3)) except Exception: logger.debug('RE Exit', exc_info=True) finally: self.cleanup_RE() m1.mv(currPos1) m2.mv(currPos2) m3.mv(currPos3) def dscan(self, motor, start, end, nsteps, nEvents, record=None, use_l3t=False): self.cleanup_RE() daq.configure(nEvents, record=record, controls=[motor], use_l3t=use_l3t) currPos = motor.wm() try: RE(scan([daq], motor, currPos + start, currPos + end, nsteps)) except Exception: logger.debug('RE Exit', exc_info=True) finally: self.cleanup_RE() motor.mv(currPos) def pv_dscan(self, signal, start, end, nsteps, nEvents, record=None, use_l3t=False): self.cleanup_RE() daq.configure(nEvents, record=record, controls=[signal], use_l3t=use_l3t) currPos = signal.get() try: RE(scan([daq], signal, currPos + start, currPos + end, nsteps)) except Exception: logger.debug('RE Exit', exc_info=True) finally: self.cleanup_RE() signal.put(currPos) def a2scan(self, m1, a1, b1, m2, a2, b2, nsteps, nEvents, record=True, use_l3t=False): self.cleanup_RE() daq.configure(nEvents, record=record, controls=[m1, m2], use_l3t=use_l3t) try: RE(scan([daq], m1, a1, b1, m2, a2, b2, nsteps)) except Exception: logger.debug('RE Exit', exc_info=True) finally: self.cleanup_RE() def a3scan(self, m1, a1, b1, m2, a2, b2, m3, a3, b3, nsteps, nEvents, record=True): self.cleanup_RE() daq.configure(nEvents, record=record, controls=[m1, m2, m3]) try: RE(scan([daq], m1, a1, b1, m2, a2, b2, m3, a3, b3, nsteps)) except Exception: logger.debug('RE Exit', exc_info=True) finally: self.cleanup_RE() def delay_scan(self, start, end, sweep_time, record=None, use_l3t=False, duration=None): """Delay scan with the daq.""" self.cleanup_RE() daq.configure(events=None, duration=None, record=record, use_l3t=use_l3t, controls=[lxt_fast]) try: RE( delay_scan(daq, lxt_fast, [start, end], sweep_time, duration=duration)) except Exception: logger.debug('RE Exit', exc_info=True) finally: self.cleanup_RE() def empty_delay_scan(self, start, end, sweep_time, record=None, use_l3t=False, duration=None): """Delay scan without the daq.""" self.cleanup_RE() #daq.configure(events=None, duration=None, record=record, # use_l3t=use_l3t, controls=[lxt_fast]) try: RE( delay_scan(None, lxt_fast, [start, end], sweep_time, duration=duration)) except Exception: logger.debug('RE Exit', exc_info=True) finally: self.cleanup_RE() def cleanup_RE(self): if not RE.state.is_idle: print('Cleaning up RunEngine') print('Stopping previous run') try: RE.stop() except Exception: pass