From 4f6a49c5387b9208d43ab9526efee56aa4f2af3a Mon Sep 17 00:00:00 2001 From: gobbo_a Date: Mon, 15 Dec 2025 16:53:16 +0100 Subject: [PATCH] dez 2025 --- config/config.properties | 28 +- config/variables.properties | 8 +- devices/CurrentCamera.properties | 22 +- devices/WireScanner motor.properties | 8 +- devices/cam_server.properties | 10 +- script/CPython/k_fit.py | 25 + script/Devices/Elements.py | 26 + script/Diagnostics/BLM_ROI_finetune.py | 6 +- script/Diagnostics/WSCdata.py | 176 +++++ script/Diagnostics/WireScan.py | 24 +- script/RFscan/GunEnergyScan.py | 6 +- script/RFscan/phase_scan_caqtdm.py | 63 +- script/Undulators/EnergyLoss_AR.py | 54 ++ script/Undulators/EnergyLoss_AT.py | 54 ++ script/Undulators/K_AR_KtoTaper.py | 37 + script/Undulators/K_AR_lasing_off.py | 6 +- script/Undulators/K_AR_taper.py | 1 - script/Undulators/K_AT_KtoTaper.py | 37 + script/Undulators/K_AT_color1_lasing_off.py | 4 +- script/Undulators/K_AT_color2_lasing_off.py | 4 +- script/Undulators/K_AT_lasing_off.py | 4 +- script/Undulators/K_AT_taper.py | 4 + script/Undulators/K_AT_taper1.py | 4 + script/Undulators/K_AT_taper2.py | 4 + script/Undulators/und_scan.py | 151 +++- script/Undulators/und_scan_global.py | 48 +- script/Undulators/und_scan_set.py | 4 +- script/local.py | 830 ++++++++++---------- script/test/TestBsreadCamera.py | 1 + script/test/TestWscData.py | 23 + script/test/test.py | 8 + script/test/test_bg_scan.py | 12 + script/test/test_daqbuf.py | 16 + script/test/test_daqbuf_nested.py | 2 + script/test/test_data-txt.py | 6 + script/test/test_data_txt.py | 6 + script/test/test_nested.py | 10 + 37 files changed, 1214 insertions(+), 518 deletions(-) create mode 100644 script/CPython/k_fit.py create mode 100644 script/Diagnostics/WSCdata.py create mode 100644 script/Undulators/EnergyLoss_AR.py create mode 100644 script/Undulators/EnergyLoss_AT.py create mode 100644 script/Undulators/K_AR_KtoTaper.py create mode 100644 script/Undulators/K_AT_KtoTaper.py mode change 100755 => 100644 script/local.py create mode 100644 script/test/TestWscData.py create mode 100644 script/test/test.py create mode 100644 script/test/test_bg_scan.py create mode 100644 script/test/test_daqbuf.py create mode 100644 script/test/test_daqbuf_nested.py create mode 100644 script/test/test_data-txt.py create mode 100644 script/test/test_data_txt.py create mode 100644 script/test/test_nested.py diff --git a/config/config.properties b/config/config.properties index 653d957..0d93163 100755 --- a/config/config.properties +++ b/config/config.properties @@ -1,14 +1,17 @@ -#Wed Aug 13 10:45:06 CEST 2025 +#Tue Oct 28 16:49:26 CET 2025 autoSaveScanData=true simulation=false +dataScanAutoSave=true xscanCrlogicChannel=null dataScanSaveOutput=false +scanPreserveTypes=false userAuthenticator= dataScanStrategy=default dataScanSaveScript=false notifiedTasks=null parallelInitialization=false fdaSerialization=false +consoleJournal=false scanDataRelease=false dataTransferPath=null scanStreamingPort=-1 @@ -17,10 +20,12 @@ xscanAppendSuffix=true devicePoolFile={config}/devices.properties hostName= disableEmbeddedAttributes=false +scanSaveTimestamps=false +commandTimeToLive=600000 serverPort=8090 versionTrackingEnabled=true dataPath={data}/{year}/{month}/{day}/{date}_{time}_{name} -serverEnabled=true +serverEnabled=false depthDimension=0 logLevel=Fine dataLayout=sf @@ -31,27 +36,40 @@ deviceUpdateStrategyFile={config}/update.properties terminalEnabled=false notificationLevel=Off terminalPort=3579 +commandQueueSize=-1 dataTransferUser=null xscanContinuousUpdate=false -versionTrackingLogin=auto +scanLazyTableCreation=false +versionTrackingLogin= noBytecodeFiles=false +scanSaveMeta=true versionTrackingRemote=https\://gitea.psi.ch/pshell_config/sf-op.git +scanAutoSave=true dataScanLazyTableCreation=false pythonHome= xscanMoveTimeout=600 +commandStatistics=false +serverHostName=null commandExecutionEvents=false logDaysToLive=30 xscanCrlogicSimulated=false +dataDepthDimension=0 logLevelConsole=Off filePermissionsConfig=Default scanStreamerPort=-1 +dataEmbeddedAttributes=false dataScanSaveSetpoints=false +scanSaveLogs=true +serverCommandsHidden=false versionTrackingManual=true dataTransferMode=Off userManagement=false instanceName=OP dataServerPort=-1 +notificationTasks= hideServerMessages=false +scanReleaseRecords=false +scanDefaultTag=null dataScanReleaseRecords=false dataScanPreserveTypes=false dataScanFlushRecords=false @@ -59,10 +77,14 @@ filePermissionsLogs=Public logPath={logs}/{date}_{time} filePermissionsScripts=Public xscanCrlogicPrefix=null +dataFormat=null +dataScanSaveLogs=true tasksFile={config}/tasks.properties filePermissionsData=Default xscanCrlogicAbortable=true createSessionFiles=false +dataScanStreamerPort=-1 +scanFlushRecords=false dataProvider=default xscanCrlogicIoc=null saveCommandStatistics=false diff --git a/config/variables.properties b/config/variables.properties index b729c5a..d5c8971 100755 --- a/config/variables.properties +++ b/config/variables.properties @@ -1,4 +1,4 @@ -#Tue Aug 12 11:55:44 CEST 2025 -LastRunDate=250812 -FileSequentialNumber=15036 -DaySequentialNumber=1 +#Thu Dec 11 15:41:25 CET 2025 +LastRunDate=251211 +FileSequentialNumber=16000 +DaySequentialNumber=17 diff --git a/devices/CurrentCamera.properties b/devices/CurrentCamera.properties index 192eebe..1996b76 100755 --- a/devices/CurrentCamera.properties +++ b/devices/CurrentCamera.properties @@ -1,8 +1,4 @@ -#Wed Aug 13 09:56:10 CEST 2025 -\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000= -\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000= -\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000= -\u0000\u0000\u0000\u0000\u0000= +#Mon Dec 15 10:58:09 CET 2025 \u0000\u0000\u0000= \u0000\u0000= \u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000= @@ -10,29 +6,33 @@ \u0000\u0000\u0000\u0000= \u0000\u0000\u0000\u0000\u0000\u0000= \u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000= +\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000= +\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000= +\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000\u0000= +\u0000\u0000\u0000\u0000\u0000= colormapLogarithmic=false -spatialCalScaleX=-6.675964236212876 -spatialCalScaleY=-6.557376778528833 +spatialCalScaleX=-6.67596435546875 +spatialCalScaleY=-6.5573768833705355 serverURL=null rescaleOffset=0.0 roiWidth=-1 colormap=Flame imageWidth=1744 invert=false -colormapMin=500.0 +colormapMin=100.0 rotationCrop=false 1= roiHeight=-1 colormapAutomatic=true roiY=0 roiX=0 -spatialCalOffsetY=-901.0000457331158 -spatialCalOffsetX=-787.0000049160263 +spatialCalOffsetY=-312.00000361676905 +spatialCalOffsetX=298.0 scale=1.0 regionStart= grayscale=false rtY=1 -colormapMax=65000.0 +colormapMax=30000.0 spat= rotation=0.0 rescaleFactor=1.0 diff --git a/devices/WireScanner motor.properties b/devices/WireScanner motor.properties index 3f3173b..ebeacfc 100755 --- a/devices/WireScanner motor.properties +++ b/devices/WireScanner motor.properties @@ -1,6 +1,6 @@ -#Mon Jul 14 16:37:26 CEST 2025 +#Thu Dec 11 15:41:25 CET 2025 offset=0.0 -maxValue=51500.0 +maxValue=68500.0 precision=1 rotation=false scale=1.0 @@ -10,10 +10,10 @@ maxSpeed=2000.0 resolution=0.1 homingType=None startRetries=1 -minValue=-56937.0 +minValue=-70000.0 unit=um defaultSpeed=2000.0 hasEnable=false sign_bit=0 monitorByPosition=false -minSpeed=50.0 +minSpeed=5.0 diff --git a/devices/cam_server.properties b/devices/cam_server.properties index e90eede..fb33f42 100755 --- a/devices/cam_server.properties +++ b/devices/cam_server.properties @@ -1,11 +1,11 @@ -#Mon Jun 30 17:38:12 CEST 2025 -spatialCalOffsetY=-829.0000262816876 -spatialCalOffsetX=-861.0000211619925 +#Fri Oct 03 16:35:45 CEST 2025 +spatialCalOffsetY=-795.999998704586 +spatialCalOffsetX=-873.9999719532899 colormapLogarithmic=false scale=1.0 grayscale=false -spatialCalScaleX=-18.90359092620482 -spatialCalScaleY=-19.607842977590828 +spatialCalScaleX=-20.775623700157773 +spatialCalScaleY=-21.55172349612865 colormapMax=NaN rescaleOffset=0.0 roiWidth=-1 diff --git a/script/CPython/k_fit.py b/script/CPython/k_fit.py new file mode 100644 index 0000000..6dbef46 --- /dev/null +++ b/script/CPython/k_fit.py @@ -0,0 +1,25 @@ +import numpy as np +from scipy.optimize import least_squares + +def k_fit(y_dat): + """ + Fit linear and quadratic to K total + """ + def optimize_func(a, y, n): + result = [] + i, j = 0, 0 + for u in range(len(y)): + val = y[0] + a[0] * i + a[1] * j**2 - y[u] + i = i + 1 + if u >= n: j = j + 1 + result.append(val) + return result + mini = None + for n in range(len(y_dat)): + a_init = (0.0001, 0.0001) + result = least_squares(optimize_func, a_init, args=(y_dat, n)) + if mini is None or result["cost"] < mini: + mini = result["cost"] + n_fit = n + a_fit = result["x"] + return (a_fit[0], a_fit[1], n_fit) \ No newline at end of file diff --git a/script/Devices/Elements.py b/script/Devices/Elements.py index 5344fee..f0d3a68 100755 --- a/script/Devices/Elements.py +++ b/script/Devices/Elements.py @@ -420,3 +420,29 @@ def set_wire_scan_range(wsc, wire, start, end): caput((wsc + ":" + sel[wire] +"_START_SP"), start) caput((wsc + ":" + sel[wire] +"_END_SP"), end) + + + +def disable_blms(wire_scanner, debug=True): + init_state = {} + blms = WSC_data.get(wire_scanner, {}).get("BLM", []) + + for blm in blms: + init_state[blm] = is_blm_enabled(blm) + + for blm, state in init_state.items(): + if state != (False, False): + if debug: + print "Disable: ", blm, state + else: + set_blm_enabled(False, blm) + return init_state + +def reenable_blms(init_state, debug=True): + for blm, state in init_state.items(): + if state != (False, False): + if debug: + print "Restore: ", blm, state + else: + set_blm_enabled(state, blm) + diff --git a/script/Diagnostics/BLM_ROI_finetune.py b/script/Diagnostics/BLM_ROI_finetune.py index 92223e7..0cf74c5 100644 --- a/script/Diagnostics/BLM_ROI_finetune.py +++ b/script/Diagnostics/BLM_ROI_finetune.py @@ -1,9 +1,9 @@ # shift BLM ROI by desired offset in us and reinitialise ioc -blm = "SARUN05-DBLM030" -#ioc = "SARUN04-DBLM516" +blm = "SARCL01-DBLM195" +offset = 0.000 # us + ioc = caget(blm + ":PLL-LOCKED-OP-CALC.INPA").split()[0] ioc = ioc.split(':')[0] -offset = 0.000 # us PIX = 2.33426704 # 1 / (124.8 MHz * 3) = 2.33426704 ns evr = caget(blm + ":GPAC-DELAY-OP.INPA").split()[0] delay = caget(evr) diff --git a/script/Diagnostics/WSCdata.py b/script/Diagnostics/WSCdata.py new file mode 100644 index 0000000..209eeed --- /dev/null +++ b/script/Diagnostics/WSCdata.py @@ -0,0 +1,176 @@ +#WSC config +WSC_data = {"SINDI01-DWSC090": {"BLM": ["SINLH02-DBLM230", "SINLH02-DBLM235", "SINDI02-DBLM025", "SINDI02-DBLM085", + "S10DI01-DBLM015", "S10DI01-DBLM045", "S10CB04-DBLM240", "S10CB06-DBLM240", + "S10CB08-DBLM240", "S10BC01-DBLM065", "S20CB02-DBLM435", "S20SY02-DBLM075", + "S20SY03-DBLM025", "S20SY03-DBLM110", "S30CB01-DBLM445", "S30CB02-DBLM415"]}, + "S10BC01-DWSC030": {"BLM": ["SINLH02-DBLM230", "SINLH02-DBLM235", "SINDI02-DBLM025", "SINDI02-DBLM085", + "S10DI01-DBLM015", "S10DI01-DBLM045", "S10CB04-DBLM240", "S10CB06-DBLM240", + "S10CB08-DBLM240", "S10BC01-DBLM065", "S20CB02-DBLM435", "S20SY02-DBLM075", + "S20SY03-DBLM025", "S20SY03-DBLM110", "S30CB01-DBLM445", "S30CB02-DBLM415"]}, + "S10CB03-DWSC440": {"BLM": ["SINLH02-DBLM230", "SINLH02-DBLM235", "SINDI02-DBLM025", "SINDI02-DBLM085", + "S10DI01-DBLM015", "S10DI01-DBLM045", "S10CB04-DBLM240", "S10CB06-DBLM240", + "S10CB08-DBLM240", "S10BC01-DBLM065", "S20CB02-DBLM435", "S20SY02-DBLM075", + "S20SY03-DBLM025", "S20SY03-DBLM110", "S30CB01-DBLM445", "S30CB02-DBLM415"]}, + "S10CB05-DWSC440": {"BLM": ["SINLH02-DBLM230", "SINLH02-DBLM235", "SINDI02-DBLM025", "SINDI02-DBLM085", + "S10DI01-DBLM015", "S10DI01-DBLM045", "S10CB04-DBLM240", "S10CB06-DBLM240", + "S10CB08-DBLM240", "S10BC01-DBLM065", "S20CB02-DBLM435", "S20SY02-DBLM075", + "S20SY03-DBLM025", "S20SY03-DBLM110", "S30CB01-DBLM445", "S30CB02-DBLM415"]}, + "S10CB07-DWSC440": {"BLM": ["SINLH02-DBLM230", "SINLH02-DBLM235", "SINDI02-DBLM025", "SINDI02-DBLM085", + "S10DI01-DBLM015", "S10DI01-DBLM045", "S10CB04-DBLM240", "S10CB06-DBLM240", + "S10CB08-DBLM240", "S10BC01-DBLM065", "S20CB02-DBLM435", "S20SY02-DBLM075", + "S20SY03-DBLM025", "S20SY03-DBLM110", "S30CB01-DBLM445", "S30CB02-DBLM415"]}, + "S10DI01-DWSC010": {"BLM": ["SINLH02-DBLM230", "SINLH02-DBLM235", "SINDI02-DBLM025", "SINDI02-DBLM085", + "S10DI01-DBLM015", "S10DI01-DBLM045", "S10CB04-DBLM240", "S10CB06-DBLM240", + "S10CB08-DBLM240", "S10BC01-DBLM065", "S20CB02-DBLM435", "S20SY02-DBLM075", + "S20SY03-DBLM025", "S20SY03-DBLM110", "S30CB01-DBLM445", "S30CB02-DBLM415"]}, + "S20CB01-DWSC440": {"BLM": ["S10DI01-DBLM015", "S10DI01-DBLM045", "S10CB04-DBLM240", "S10CB06-DBLM240", + "S10CB08-DBLM240", "S10BC01-DBLM065", "S20CB02-DBLM435", "S20SY02-DBLM075", + "S20SY03-DBLM025", "S20SY03-DBLM110", "S30CB01-DBLM445", "S30CB02-DBLM415", + "S30CB06-DBLM445", "S30CB10-DBLM445", "S30CB14-DBLM445", "SATSY03-DBLM085", + "SATCL01-DBLM135", "SATCB01-DBLM245", "SATDI01-DBLM095", "SATDI01-DBLM105", + "SATDI01-DBLM225", "SATDI01-DBLM305", "SATCL02-DBLM295", "SATCL02-DBLM435", + "SATMA01-DBLM065"]}, + "S20SY01-DWSC070": {"BLM": ["S10DI01-DBLM015", "S10DI01-DBLM045", "S10CB04-DBLM240", "S10CB06-DBLM240", + "S10CB08-DBLM240", "S10BC01-DBLM065", "S20CB02-DBLM435", "S20SY02-DBLM075", + "S20SY03-DBLM025", "S20SY03-DBLM110", "S30CB01-DBLM445", "S30CB02-DBLM415", + "S30CB06-DBLM445", "S30CB10-DBLM445", "S30CB14-DBLM445", "SATSY03-DBLM085", + "SATCL01-DBLM135", "SATCB01-DBLM245", "SATDI01-DBLM095", "SATDI01-DBLM105", + "SATDI01-DBLM225", "SATDI01-DBLM305", "SATCL02-DBLM295", "SATCL02-DBLM435", + "SATMA01-DBLM065"]}, + "S20SY02-DWSC160": {"BLM": ["S10DI01-DBLM015", "S10DI01-DBLM045", "S10CB04-DBLM240", "S10CB06-DBLM240", + "S10CB08-DBLM240", "S10BC01-DBLM065", "S20CB02-DBLM435", "S20SY02-DBLM075", + "S20SY03-DBLM025", "S20SY03-DBLM110", "S30CB01-DBLM445", "S30CB02-DBLM415", + "S30CB06-DBLM445", "S30CB10-DBLM445", "S30CB14-DBLM445", "SATSY03-DBLM085", + "SATCL01-DBLM135", "SATCB01-DBLM245", "SATDI01-DBLM095", "SATDI01-DBLM105", + "SATDI01-DBLM225", "SATDI01-DBLM305", "SATCL02-DBLM295", "SATCL02-DBLM435", + "SATMA01-DBLM065"]}, + "S20SY03-DWSC090": {"BLM": ["S10DI01-DBLM015", "S10DI01-DBLM045", "S10CB04-DBLM240", "S10CB06-DBLM240", + "S10CB08-DBLM240", "S10BC01-DBLM065", "S20CB02-DBLM435", "S20SY02-DBLM075", + "S20SY03-DBLM025", "S20SY03-DBLM110", "S30CB01-DBLM445", "S30CB02-DBLM415", + "S30CB06-DBLM445", "S30CB10-DBLM445", "S30CB14-DBLM445", "SATSY03-DBLM085", + "SATCL01-DBLM135", "SATCB01-DBLM245", "SATDI01-DBLM095", "SATDI01-DBLM105", + "SATDI01-DBLM225", "SATDI01-DBLM305", "SATCL02-DBLM295", "SATCL02-DBLM435", + "SATMA01-DBLM065"]}, + "S30CB01-DWSC440": {"BLM": ["S20CB02-DBLM435", "S20SY02-DBLM075", + "S20SY03-DBLM025", "S20SY03-DBLM110", "S30CB01-DBLM445", "S30CB02-DBLM415", + "S30CB06-DBLM445", "S30CB10-DBLM445", "S30CB14-DBLM445", "SARCL01-DBLM195", + "SARCL02-DBLM050", "SARCL02-DBLM355", "SARUN01-DBLM065", "SARUN03-DBLM030", + "SARUN04-DBLM030", "SARUN05-DBLM030", "SARUN06-DBLM030", "SARUN07-DBLM030", + "SARUN08-DBLM030", "SARUN09-DBLM030", "SARUN10-DBLM030", "SARUN11-DBLM030", + "SARUN12-DBLM030", "SARUN13-DBLM030", "SARUN14-DBLM030", "SARUN15-DBLM030", + "SARUN15-DBLM035", "SARUN20-DBLM035", "SATSY03-DBLM085", "SATCL01-DBLM135", + "SATCB01-DBLM245", "SATDI01-DBLM095", "SATDI01-DBLM105", "SATDI01-DBLM225", + "SATDI01-DBLM305", "SATCL02-DBLM295", "SATCL02-DBLM435", "SATMA01-DBLM065", + "SATUN05-DBLM405", "SATUN06-DBLM075", "SATUN07-DBLM075", "SATUN08-DBLM075", + "SATUN09-DBLM075", "SATUN10-DBLM075", "SATUN11-DBLM075", "SATUN12-DBLM075", + "SATUN14-DBLM405", "SATUN15-DBLM075", "SATUN16-DBLM075", "SATUN17-DBLM075", + "SATUN18-DBLM075", "SATUN19-DBLM075", "SATUN22-DBLM075", "SATBD01-DBLM205"]}, + "S30CB05-DWSC440": {"BLM": ["S20CB02-DBLM435", "S20SY02-DBLM075", + "S20SY03-DBLM025", "S20SY03-DBLM110", "S30CB01-DBLM445", "S30CB02-DBLM415", + "S30CB06-DBLM445", "S30CB10-DBLM445", "S30CB14-DBLM445", "SARCL01-DBLM195", + "SARCL02-DBLM050", "SARCL02-DBLM355", "SARUN01-DBLM065", "SARUN03-DBLM030", + "SARUN04-DBLM030", "SARUN05-DBLM030", "SARUN06-DBLM030", "SARUN07-DBLM030", + "SARUN08-DBLM030", "SARUN09-DBLM030", "SARUN10-DBLM030", "SARUN11-DBLM030", + "SARUN12-DBLM030", "SARUN13-DBLM030", "SARUN14-DBLM030", "SARUN15-DBLM030", + "SARUN15-DBLM035", "SARUN20-DBLM035", "SATSY03-DBLM085", "SATCL01-DBLM135", + "SATCB01-DBLM245", "SATDI01-DBLM095", "SATDI01-DBLM105", "SATDI01-DBLM225", + "SATDI01-DBLM305", "SATCL02-DBLM295", "SATCL02-DBLM435", "SATMA01-DBLM065", + "SATUN05-DBLM405", "SATUN06-DBLM075", "SATUN07-DBLM075", "SATUN08-DBLM075", + "SATUN09-DBLM075", "SATUN10-DBLM075", "SATUN11-DBLM075", "SATUN12-DBLM075", + "SATUN14-DBLM405", "SATUN15-DBLM075", "SATUN16-DBLM075", "SATUN17-DBLM075", + "SATUN18-DBLM075", "SATUN19-DBLM075", "SATUN22-DBLM075", "SATBD01-DBLM205"]}, + "S30CB09-DWSC440": {"BLM": ["S20CB02-DBLM435", "S20SY02-DBLM075", + "S20SY03-DBLM025", "S20SY03-DBLM110", "S30CB01-DBLM445", "S30CB02-DBLM415", + "S30CB06-DBLM445", "S30CB10-DBLM445", "S30CB14-DBLM445", "SARCL01-DBLM195", + "SARCL02-DBLM050", "SARCL02-DBLM355", "SARUN01-DBLM065", "SARUN03-DBLM030", + "SARUN04-DBLM030", "SARUN05-DBLM030", "SARUN06-DBLM030", "SARUN07-DBLM030", + "SARUN08-DBLM030", "SARUN09-DBLM030", "SARUN10-DBLM030", "SARUN11-DBLM030", + "SARUN12-DBLM030", "SARUN13-DBLM030", "SARUN14-DBLM030", "SARUN15-DBLM030", + "SARUN15-DBLM035", "SARUN20-DBLM035", "SATSY03-DBLM085", "SATCL01-DBLM135", + "SATCB01-DBLM245", "SATDI01-DBLM095", "SATDI01-DBLM105", "SATDI01-DBLM225", + "SATDI01-DBLM305", "SATCL02-DBLM295", "SATCL02-DBLM435", "SATMA01-DBLM065", + "SATUN05-DBLM405", "SATUN06-DBLM075", "SATUN07-DBLM075", "SATUN08-DBLM075", + "SATUN09-DBLM075", "SATUN10-DBLM075", "SATUN11-DBLM075", "SATUN12-DBLM075", + "SATUN14-DBLM405", "SATUN15-DBLM075", "SATUN16-DBLM075", "SATUN17-DBLM075", + "SATUN18-DBLM075", "SATUN19-DBLM075", "SATUN22-DBLM075", "SATBD01-DBLM205"]}, + "S30CB13-DWSC440": {"BLM": ["S20CB02-DBLM435", "S20SY02-DBLM075", + "S20SY03-DBLM025", "S20SY03-DBLM110", "S30CB01-DBLM445", "S30CB02-DBLM415", + "S30CB06-DBLM445", "S30CB10-DBLM445", "S30CB14-DBLM445", "SARCL01-DBLM195", + "SARCL02-DBLM050", "SARCL02-DBLM355", "SARUN01-DBLM065", "SARUN03-DBLM030", + "SARUN04-DBLM030", "SARUN05-DBLM030", "SARUN06-DBLM030", "SARUN07-DBLM030", + "SARUN08-DBLM030", "SARUN09-DBLM030", "SARUN10-DBLM030", "SARUN11-DBLM030", + "SARUN12-DBLM030", "SARUN13-DBLM030", "SARUN14-DBLM030", "SARUN15-DBLM030", + "SARUN15-DBLM035", "SARUN20-DBLM035", "SATSY03-DBLM085", "SATCL01-DBLM135", + "SATCB01-DBLM245", "SATDI01-DBLM095", "SATDI01-DBLM105", "SATDI01-DBLM225", + "SATDI01-DBLM305", "SATCL02-DBLM295", "SATCL02-DBLM435", "SATMA01-DBLM065", + "SATUN05-DBLM405", "SATUN06-DBLM075", "SATUN07-DBLM075", "SATUN08-DBLM075", + "SATUN09-DBLM075", "SATUN10-DBLM075", "SATUN11-DBLM075", "SATUN12-DBLM075", + "SATUN14-DBLM405", "SATUN15-DBLM075", "SATUN16-DBLM075", "SATUN17-DBLM075", + "SATUN18-DBLM075", "SATUN19-DBLM075", "SATUN22-DBLM075", "SATBD01-DBLM205"]}, + "SARCL01-DWSC160": {"BLM": ["S30CB01-DBLM445", "S30CB02-DBLM415", + "S30CB06-DBLM445", "S30CB10-DBLM445", "S30CB14-DBLM445", "SARCL01-DBLM195", + "SARCL02-DBLM050", "SARCL02-DBLM355", "SARUN01-DBLM065", "SARUN03-DBLM030", + "SARUN04-DBLM030", "SARUN05-DBLM030", "SARUN06-DBLM030", "SARUN07-DBLM030", + "SARUN08-DBLM030", "SARUN09-DBLM030", "SARUN10-DBLM030", "SARUN11-DBLM030", + "SARUN12-DBLM030", "SARUN13-DBLM030", "SARUN14-DBLM030", "SARUN15-DBLM030", + "SARUN15-DBLM035", "SARUN20-DBLM035", "SATUN05-DBLM405", "SATUN06-DBLM075", + "SATUN07-DBLM075", "SATUN08-DBLM075", + "SATUN09-DBLM075", "SATUN10-DBLM075", "SATUN11-DBLM075", "SATUN12-DBLM075", + "SATUN14-DBLM405", "SATUN15-DBLM075", "SATUN16-DBLM075", "SATUN17-DBLM075", + "SATUN18-DBLM075", "SATUN19-DBLM075", "SATUN22-DBLM075", "SATBD01-DBLM205"]}, + "SARCL02-DWSC235": {"BLM": ["S30CB01-DBLM445", "S30CB02-DBLM415", + "S30CB06-DBLM445", "S30CB10-DBLM445", "S30CB14-DBLM445", "SARCL01-DBLM195", + "SARCL02-DBLM050", "SARCL02-DBLM355", "SARUN01-DBLM065", "SARUN03-DBLM030", + "SARUN04-DBLM030", "SARUN05-DBLM030", "SARUN06-DBLM030", "SARUN07-DBLM030", + "SARUN08-DBLM030", "SARUN09-DBLM030", "SARUN10-DBLM030", "SARUN11-DBLM030", + "SARUN12-DBLM030", "SARUN13-DBLM030", "SARUN14-DBLM030", "SARUN15-DBLM030", + "SARUN15-DBLM035", "SARUN20-DBLM035", "SATUN05-DBLM405", "SATUN06-DBLM075", + "SATUN07-DBLM075", "SATUN08-DBLM075", + "SATUN09-DBLM075", "SATUN10-DBLM075", "SATUN11-DBLM075", "SATUN12-DBLM075", + "SATUN14-DBLM405", "SATUN15-DBLM075", "SATUN16-DBLM075", "SATUN17-DBLM075", + "SATUN18-DBLM075", "SATUN19-DBLM075", "SATUN22-DBLM075", "SATBD01-DBLM205"]}, + "SARMA02-DWSC060": {"BLM": ["S30CB01-DBLM445", "S30CB02-DBLM415", + "S30CB06-DBLM445", "S30CB10-DBLM445", "S30CB14-DBLM445", "SARCL01-DBLM195", + "SARCL02-DBLM050", "SARCL02-DBLM355", "SARUN01-DBLM065", "SARUN03-DBLM030", + "SARUN04-DBLM030", "SARUN05-DBLM030", "SARUN06-DBLM030", "SARUN07-DBLM030", + "SARUN08-DBLM030", "SARUN09-DBLM030", "SARUN10-DBLM030", "SARUN11-DBLM030", + "SARUN12-DBLM030", "SARUN13-DBLM030", "SARUN14-DBLM030", "SARUN15-DBLM030", + "SARUN15-DBLM035", "SARUN20-DBLM035", "SATUN05-DBLM405", "SATUN06-DBLM075", + "SATUN07-DBLM075", "SATUN08-DBLM075", + "SATUN09-DBLM075", "SATUN10-DBLM075", "SATUN11-DBLM075", "SATUN12-DBLM075", + "SATUN14-DBLM405", "SATUN15-DBLM075", "SATUN16-DBLM075", "SATUN17-DBLM075", + "SATUN18-DBLM075", "SATUN19-DBLM075", "SATUN22-DBLM075", "SATBD01-DBLM205"]}, + "SARUN20-DWSC010": {"BLM": ["S30CB01-DBLM445", "S30CB02-DBLM415", + "S30CB06-DBLM445", "S30CB10-DBLM445", "S30CB14-DBLM445", "SARCL01-DBLM195", + "SARCL02-DBLM050", "SARCL02-DBLM355", "SARUN01-DBLM065", "SARUN03-DBLM030", + "SARUN04-DBLM030", "SARUN05-DBLM030", "SARUN06-DBLM030", "SARUN07-DBLM030", + "SARUN08-DBLM030", "SARUN09-DBLM030", "SARUN10-DBLM030", "SARUN11-DBLM030", + "SARUN12-DBLM030", "SARUN13-DBLM030", "SARUN14-DBLM030", "SARUN15-DBLM030", + "SARUN15-DBLM035", "SARUN20-DBLM035", "SATUN05-DBLM405", "SATUN06-DBLM075", + "SATUN07-DBLM075", "SATUN08-DBLM075", + "SATUN09-DBLM075", "SATUN10-DBLM075", "SATUN11-DBLM075", "SATUN12-DBLM075", + "SATUN14-DBLM405", "SATUN15-DBLM075", "SATUN16-DBLM075", "SATUN17-DBLM075", + "SATUN18-DBLM075", "SATUN19-DBLM075", "SATUN22-DBLM075", "SATBD01-DBLM205"]}, + "SATSY03-DWSC110": {"BLM": ["S20CB02-DBLM435", "S20SY02-DBLM075", + "S20SY03-DBLM025", "S20SY03-DBLM110", "S30CB01-DBLM445", "S30CB02-DBLM415", + "S30CB06-DBLM445", "S30CB10-DBLM445", "S30CB14-DBLM445", "SARCL01-DBLM195", + "SARCL02-DBLM050", "SARCL02-DBLM355", "SATSY03-DBLM085", "SATCL01-DBLM135", + "SATCB01-DBLM245", "SATDI01-DBLM095", "SATDI01-DBLM105", "SATDI01-DBLM225", + "SATDI01-DBLM305", "SATCL02-DBLM295", "SATCL02-DBLM435", "SATMA01-DBLM065"]}, + "SATDI01-DWSC290": {"BLM": ["S20CB02-DBLM435", "S20SY02-DBLM075", + "S20SY03-DBLM025", "S20SY03-DBLM110", "S30CB01-DBLM445", "S30CB02-DBLM415", + "S30CB06-DBLM445", "S30CB10-DBLM445", "S30CB14-DBLM445", "SARCL01-DBLM195", + "SARCL02-DBLM050", "SARCL02-DBLM355", "SATSY03-DBLM085", "SATCL01-DBLM135", + "SATCB01-DBLM245", "SATDI01-DBLM095", "SATDI01-DBLM105", "SATDI01-DBLM225", + "SATDI01-DBLM305", "SATCL02-DBLM295", "SATCL02-DBLM435", "SATMA01-DBLM065"]}, + "SATBD01-DWSC110": {"BLM": ["S30CB01-DBLM445", "S30CB02-DBLM415", "S30CB06-DBLM445", "S30CB10-DBLM445", + "S30CB14-DBLM445", "SARCL01-DBLM195", "SARCL02-DBLM050", "SARCL02-DBLM355", + "SARUN01-DBLM065", "SARUN03-DBLM030", "SARUN04-DBLM030", "SARUN05-DBLM030", + "SARUN06-DBLM030", "SARUN07-DBLM030", "SARUN08-DBLM030", "SARUN09-DBLM030", + "SARUN10-DBLM030", "SARUN11-DBLM030", "SARUN12-DBLM030", "SARUN13-DBLM030", + "SARUN14-DBLM030", "SARUN15-DBLM030", "SARUN15-DBLM035", "SARUN20-DBLM035", + "SATUN05-DBLM405", "SATUN06-DBLM075", "SATUN07-DBLM075", "SATUN08-DBLM075", + "SATUN09-DBLM075", "SATUN10-DBLM075", "SATUN11-DBLM075", "SATUN12-DBLM075", + "SATUN14-DBLM405", "SATUN15-DBLM075", "SATUN16-DBLM075", "SATUN17-DBLM075", + "SATUN18-DBLM075", "SATUN19-DBLM075", "SATUN22-DBLM075", "SATBD01-DBLM205"]}} + diff --git a/script/Diagnostics/WireScan.py b/script/Diagnostics/WireScan.py index 84fdf76..5161ea8 100644 --- a/script/Diagnostics/WireScan.py +++ b/script/Diagnostics/WireScan.py @@ -9,6 +9,7 @@ MAX_RANGE_STEP = 3 run("Devices/Elements") run("Devices/WireScanner") run("Diagnostics/sig_process_wrapper") +run("Diagnostics/WSCdata") #LayoutSF DATA_GROUP_PREFIX = "data/" @@ -20,10 +21,10 @@ DATA_GROUP_PREFIX = "" DATASET_SUFIX = "" #Paramter parsing -prefix = args[0] if has_args else "SARCL01-DWSC160" # "SINDI01-DWSC090" # "S10DI01-DWSC010" #"S10CB07-DWSC440" #"SINDI01-DWSC090" +prefix = args[0] if has_args else "S30CB13-DWSC440" # "SARCL01-DWSC160" # "SINDI01-DWSC090" # "S10DI01-DWSC010" #"S10CB07-DWSC440" #"SINDI01-DWSC090" scan_type = args[1] if has_args else WireScanner.WireX1 scan_range = args[2] if has_args else [] -cycles = args[3] if has_args else 2 +cycles = args[3] if has_args else 1 #velocity = args[4] if has_args else 200 n_shot = args[4] if has_args else 200 bpms = args[5] if has_args else [] #get_wire_scanners_bpms(prefix) @@ -49,6 +50,8 @@ SET_BLM_WS_MODE = True SET_BLM_WS_SETTLING_TIME = 2.0 SET_BLM_WS_BS_READBACK_TIMEOUT = 10000 #ms +DISABLE_BLMS= True + ADD_CHANNELS = [] #ADD_CHANNELS = ["SARFE10-PBPG050:HAMP-INTENSITY-CAL", "SARFE10-PBIG050-EVR0:CALCI"] @@ -105,7 +108,7 @@ blm_ranges = [] blm_raws = [] blm_mins = [] snaps.append(Channel(get_repetition_rate_rb_channel(bunch))) - +blms = [x for x in blms if x is not None] for i in range (len(blms)): channels.append (("blm" + str(i+1), blms[i] + ":B" + str(bunch) + "_LOSS_RAW")) #channels.append (("blm" + str(i+1), blms[i] + ":B" + str(bunch) + "_LOSS")) @@ -502,9 +505,13 @@ def get_scan_time(): ret = ret * 2.0 + 10.0 #Tolernces print "; with tolerance = " + str(ret), return ret - + +if DISABLE_BLMS: + print "Disabling BLMs..." + init_state = disable_blms(prefix, debug=(DISABLE_BLMS=="debug")) + print "Starting scan..." -try: +try: if SET_BLM_WS_MODE and len(blms)>0: for i in range(len(blms)): start_blm_ws(blms[i], get_scan_time()) @@ -528,13 +535,16 @@ except: raise finally: try: - scanner.park(wait=False) + scanner.park(wait=(DISABLE_BLMS==True)) pass except: pass + if DISABLE_BLMS: + print "Reenabling BLMs..." + reenable_blms(init_state, debug=(DISABLE_BLMS=="debug")) if SET_BLM_WS_MODE and len(blms)>0: for i in range(len(blms)): - stop_blm_ws(blms[i]) + stop_blm_ws(blms[i]) print "Closing scanner" scanner.close() print "Closing stream" diff --git a/script/RFscan/GunEnergyScan.py b/script/RFscan/GunEnergyScan.py index d6df9ef..b0d57d4 100644 --- a/script/RFscan/GunEnergyScan.py +++ b/script/RFscan/GunEnergyScan.py @@ -104,10 +104,10 @@ dp = [abs(A) * val.mean for val in r.getReadable(1)] #Fitting and plotting try: i = p.index(max(p)) - a, b = max(i-6, 0), min(i+6, len(p)) + a, b = max(i-4, 0), min(i+5, len(p)) # 9 points (ph_p_max, p_max, ph_p_fit, p_fit, p_R2) = extremum(ph[a:b], p[a:b]) i = dp.index(min(dp)) - a, b = max(i-6, 0), min(i+6, len(dp)) + a, b = max(i-2, 0), min(i+3, len(dp)) # 5 points (ph_dp_min, dp_min, ph_dp_fit, dp_fit, dp_R2) = extremum(ph[a:b], dp[a:b]) except : print sys.exc_info() @@ -117,8 +117,6 @@ plt.addSeries(LinePlotErrorSeries("Momentum Fit", plt.getSeries(0).color)) plt.addSeries(LinePlotErrorSeries("Momentum Spread Fit", plt.getSeries(1).color, 2)) plt.getSeries(2).setData(ph_p_fit, p_fit) plt.getSeries(3).setData(ph_dp_fit, dp_fit) -#plt.getSeries(2).setData(ph_p_fit, p_fit, to_array([0.0]*len(ph_p_fit), 'd'), to_array([0.0]*len(ph_p_fit), 'd')) -#plt.getSeries(3).setData(ph_dp_fit, dp_fit, to_array([0.0]*len(ph_dp_fit), 'd'), to_array([0.0]*len(ph_dp_fit), 'd')) plt.getSeries(2).setPointsVisible(False) plt.getSeries(3).setPointsVisible(False) plt.addMarker(ph_p_max, plt.AxisId.X, "%3.2f" % ph_p_max, plt.getSeries(0).color) diff --git a/script/RFscan/phase_scan_caqtdm.py b/script/RFscan/phase_scan_caqtdm.py index ec07da2..ca378fe 100644 --- a/script/RFscan/phase_scan_caqtdm.py +++ b/script/RFscan/phase_scan_caqtdm.py @@ -24,7 +24,7 @@ bpm_val.initialize() amplt.initialize() power.initialize() phase = Positioner("Phase", station + "-RSYS:SET-VSUM-PHASE", station + "-RSYS:GET-VSUM-PHASE") -phase.config.minValue = -90.0 # cannot be zero, we need margin for scanning around 0 deg +phase.config.minValue = -90.0 # cannot be zero, we need margin for scanning around 0 deg phase.config.maxValue = 360.0 phase.config.precision = 4 # digits beyond this are ignored phase.config.resolution = 0.3 # dead-band for comparing set and get values @@ -42,27 +42,40 @@ bpm_averager = create_averager(bpm_val, nb, lat) energy0 = p0 - 0.511 A, B = energy0 / (disp * 1000), energy0 # param to convert bpm mm to MeV -#update the plot dynamically +# pause scan when beam is down +def is_beam_ok(): + mps_ma = int(caget("SIN-EMED-DTSA001:LEVEL1_MA.RVAL")) + mps_ar = int(caget("SIN-EMED-DTSA002:LEVEL1_AR.RVAL")) + mps_at = int(caget("SIN-EMED-DTSA003:LEVEL1_AT.RVAL")) + beam_ok = (mps_ma + mps_ar + mps_at == 3) + return beam_ok + +def wait_beam(): + if not is_beam_ok(): + print("Waiting for beam...") + while not is_beam_ok(): + time.sleep(0.5) + print("Beam ok") + +def before(rec): + wait_beam() + +# check for beam presence and update the plot dynamically arr_phase, arr_energy = [],[] def after(rec): - global A, B - arr_phase.append(rec.positions[0]) - arr_energy.append(A * rec.readables[0].mean + B) - caput(station + "-RSYS:GET-PHASE-ARRAY", to_array(arr_phase, 'd')) - caput(station + "-RSYS:GET-ENERGY-ARRAY", to_array(arr_energy,'d')) - caput("SF-PHASE-GLOBAL:GET-PHASE-ARRAY", to_array(arr_phase, 'd')) - caput("SF-PHASE-GLOBAL:GET-ENERGY-ARRAY", to_array(arr_energy,'d')) + if not is_beam_ok(): + print("Beam is down, invalidating record...") + rec.invalidate() + global A, B + arr_phase.append(rec.positions[0]) + arr_energy.append(A * rec.readables[0].mean + B) + caput(station + "-RSYS:GET-PHASE-ARRAY", to_array(arr_phase, 'd')) + caput(station + "-RSYS:GET-ENERGY-ARRAY", to_array(arr_energy,'d')) + caput("SF-PHASE-GLOBAL:GET-PHASE-ARRAY", to_array(arr_phase, 'd')) + caput("SF-PHASE-GLOBAL:GET-ENERGY-ARRAY", to_array(arr_energy,'d')) -#scan and plot +# scan and plot try: - caput(station + "-RSYS:GET-ONCREST-VSUM-PHASE", float('nan')) - caput(station + "-RSYS:GET-ONCREST-VSUM-AMPLT", float('nan')) - caput(station + "-RSYS:GET-ONCREST-E-GAIN", float('nan')) - caput(station + "-RSYS:GET-ONCREST-KLY-POWER", float('nan')) - caput(station + "-RSYS:GET-FIT-PHASE-ARRAY", to_array([0.0],'d')) - caput(station + "-RSYS:GET-FIT-ENERGY-ARRAY", to_array([0.0],'d')) - caput("SF-PHASE-GLOBAL:GET-FIT-PHASE-ARRAY", to_array([0.0],'d')) - caput("SF-PHASE-GLOBAL:GET-FIT-ENERGY-ARRAY", to_array([0.0],'d')) feedback_state_init = {} for feedback_channel in station_list[station]["feedback"]: feedback_state = caget(feedback_channel) @@ -78,7 +91,15 @@ try: phase.write(start) time.sleep(2.0) caput(station + "-RSYS:PHASE-SCAN-MESSAGE", "scanning " + station) - r = lscan(phase, bpm_averager, start, end, step, latency=lat, after_read = after) + caput(station + "-RSYS:GET-ONCREST-VSUM-PHASE", float('nan')) + caput(station + "-RSYS:GET-ONCREST-VSUM-AMPLT", float('nan')) + caput(station + "-RSYS:GET-ONCREST-E-GAIN", float('nan')) + caput(station + "-RSYS:GET-ONCREST-KLY-POWER", float('nan')) + caput(station + "-RSYS:GET-FIT-PHASE-ARRAY", to_array([0.0],'d')) + caput(station + "-RSYS:GET-FIT-ENERGY-ARRAY", to_array([0.0],'d')) + caput("SF-PHASE-GLOBAL:GET-FIT-PHASE-ARRAY", to_array([0.0],'d')) + caput("SF-PHASE-GLOBAL:GET-FIT-ENERGY-ARRAY", to_array([0.0],'d')) + r = lscan(phase, bpm_averager, start, end, step, latency=lat, before_read = before, after_read = after) energy = [A * val.mean + B for val in r.getReadable(0)] # convert bpm mm to MeV rf_phase = r.getPositions(0) if start < 0: @@ -141,7 +162,7 @@ finally: power.close() bpm_val.close() -#Saving metadata +# Saving metadata save_dataset ("experiment/Station" , station ) save_dataset ("scan 1/processed/Energy" , energy ) save_dataset ("scan 1/processed/Energy gain" , fit_amplitude ) @@ -159,7 +180,7 @@ set_attribute("scan 1/processed/Amplitude scale" , "Unit", "MV" ) set_attribute("scan 1/processed/Power scale" , "Unit", "MW/MV^2" ) set_attribute("scan 1/processed/Dispersion" , "Unit", "mm" ) -#Elog entry +# Elog entry if do_elog: title = "Phase scan " + station log_msg = "Data file: " + get_exec_pars().path + "\n" diff --git a/script/Undulators/EnergyLoss_AR.py b/script/Undulators/EnergyLoss_AR.py new file mode 100644 index 0000000..d0ff54a --- /dev/null +++ b/script/Undulators/EnergyLoss_AR.py @@ -0,0 +1,54 @@ +lat = 0.01 +sample = 1000 +ELECTRON_CHARGE = 1.60217663e-19 +BPM1 = "SARBD02-DBPM010:Y1-RT" +BPM2 = "SARBD02-DBPM040:Y1-RT" +DISP_BPM1 = "SARBD02-DBPM010:DISPERSION-OP" #198.0 mm natural disp. Holylist +DISP_BPM2 = "SARBD02-DBPM040:DISPERSION-OP" #397.8 mm natural disp. Holylist +SFB_BEAM_DUMP = "SFB_BEAM_DUMP_AR:ONOFF1" +LASING_OFF = "Undulators/K_AR_lasing_off.py" +LASING_ON = "Undulators/K_AR_taper.py" +BUNCH_CHARGE = "SARBD02-DBPM010:Q1-AVG" +ELECTRON_ENERGY = "SARCL02-MBND100:P-READ" +ENE_BPM1 = "SARBD02-DBPM010:PULSE-ENE-OP" +ENE_BPM2 = "SARBD02-DBPM040:PULSE-ENE-OP" +ERR_BPM1 = "SARBD02-DBPM010:PULSE-ENE-ERR-OP" +ERR_BPM2 = "SARBD02-DBPM040:PULSE-ENE-ERR-OP" +y_bpm1 = ChannelDouble(BPM1, BPM1) +y_bpm2 = ChannelDouble(BPM2, BPM2) +y_bpm2.monitored = True +y_bpm1.initialize() +y_bpm2.initialize() +y_averager_bpm1 = create_averager(y_bpm1, sample, lat) +y_averager_bpm2 = create_averager(y_bpm2, sample, lat) +feedback_state_init = caget(SFB_BEAM_DUMP) +caput(SFB_BEAM_DUMP, 0) +bpm1_las_on = y_averager_bpm1.read() +bpm2_las_on = y_averager_bpm2.read() +run(LASING_OFF) +time.sleep(1.0) +bpm1_las_off = y_averager_bpm1.read() +bpm2_las_off = y_averager_bpm2.read() +run(LASING_ON) +caput(SFB_BEAM_DUMP, feedback_state_init) +y_bpm1.close() +y_bpm2.close() +bunch_charge = caget(BUNCH_CHARGE) +ene_elect = caget(ELECTRON_ENERGY) +disp1 = caget(DISP_BPM1) * 1000 +disp2 = caget(DISP_BPM2) * 1000 +ene_bunch = ene_elect * 1e6 * bunch_charge * 1e-12 +dy_bpm1 = bpm1_las_off.mean - bpm1_las_on.mean +dy_bpm2 = bpm2_las_off.mean - bpm2_las_on.mean +pulse_energy_bpm1 = dy_bpm1 / disp1 * ene_bunch * 1000 +pulse_energy_bpm2 = dy_bpm2 / disp2 * ene_bunch * 1000 +dy_bpm1_stdev = bpm1_las_off.stdev + bpm1_las_on.stdev +dy_bpm2_stdev = bpm2_las_off.stdev + bpm2_las_on.stdev +pulse_energy_bpm1_stdev = dy_bpm1_stdev / disp1 * ene_bunch * 1000 +pulse_energy_bpm2_stdev = dy_bpm2_stdev / disp2 * ene_bunch * 1000 +print(pulse_energy_bpm1, pulse_energy_bpm1_stdev) +print(pulse_energy_bpm2, pulse_energy_bpm2_stdev) +caput(ENE_BPM1, pulse_energy_bpm1) +caput(ERR_BPM1, pulse_energy_bpm1_stdev) +caput(ENE_BPM2, pulse_energy_bpm2) +caput(ERR_BPM2, pulse_energy_bpm2_stdev) \ No newline at end of file diff --git a/script/Undulators/EnergyLoss_AT.py b/script/Undulators/EnergyLoss_AT.py new file mode 100644 index 0000000..b30c8c5 --- /dev/null +++ b/script/Undulators/EnergyLoss_AT.py @@ -0,0 +1,54 @@ +lat = 0.01 +sample = 1000 +ELECTRON_CHARGE = 1.60217663e-19 +BPM1 = "SATBD02-DBPM010:Y2-RT" +BPM2 = "SATBD02-DBPM040:Y2-RT" +DISP_BPM1 = "SATBD02-DBPM010:DISPERSION-OP" #198.0 mm natural disp. Holylist +DISP_BPM2 = "SATBD02-DBPM040:DISPERSION-OP" #397.8 mm natural disp. Holylist +SFB_BEAM_DUMP = "SFB_BEAM_DUMP_AT:ONOFF1" +LASING_OFF = "Undulators/K_AT_lasing_off.py" +LASING_ON = "Undulators/K_AT_taper.py" +BUNCH_CHARGE = "SATBD02-DBPM010:Q2-AVG" +ELECTRON_ENERGY = "SATCB01:ENE-FILT-OP" +ENE_BPM1 = "SATBD02-DBPM010:PULSE-ENE-OP" +ENE_BPM2 = "SATBD02-DBPM040:PULSE-ENE-OP" +ERR_BPM1 = "SATBD02-DBPM010:PULSE-ENE-ERR-OP" +ERR_BPM2 = "SATBD02-DBPM040:PULSE-ENE-ERR-OP" +y_bpm1 = ChannelDouble(BPM1, BPM1) +y_bpm2 = ChannelDouble(BPM2, BPM2) +y_bpm2.monitored = True +y_bpm1.initialize() +y_bpm2.initialize() +y_averager_bpm1 = create_averager(y_bpm1, sample, lat) +y_averager_bpm2 = create_averager(y_bpm2, sample, lat) +feedback_state_init = caget(SFB_BEAM_DUMP) +caput(SFB_BEAM_DUMP, 0) +bpm1_las_on = y_averager_bpm1.read() +bpm2_las_on = y_averager_bpm2.read() +run(LASING_OFF) +time.sleep(1.0) +bpm1_las_off = y_averager_bpm1.read() +bpm2_las_off = y_averager_bpm2.read() +run(LASING_ON) +caput(SFB_BEAM_DUMP, feedback_state_init) +y_bpm1.close() +y_bpm2.close() +bunch_charge = caget(BUNCH_CHARGE) +ene_elect = caget(ELECTRON_ENERGY) +disp1 = caget(DISP_BPM1) * 1000 +disp2 = caget(DISP_BPM2) * 1000 +ene_bunch = ene_elect * 1e6 * bunch_charge * 1e-12 +dy_bpm1 = bpm1_las_off.mean - bpm1_las_on.mean +dy_bpm2 = bpm2_las_off.mean - bpm2_las_on.mean +pulse_energy_bpm1 = dy_bpm1 / disp1 * ene_bunch * 1000 +pulse_energy_bpm2 = dy_bpm2 / disp2 * ene_bunch * 1000 +dy_bpm1_stdev = bpm1_las_off.stdev + bpm1_las_on.stdev +dy_bpm2_stdev = bpm2_las_off.stdev + bpm2_las_on.stdev +pulse_energy_bpm1_stdev = dy_bpm1_stdev / disp1 * ene_bunch * 1000 +pulse_energy_bpm2_stdev = dy_bpm2_stdev / disp2 * ene_bunch * 1000 +print(pulse_energy_bpm1, pulse_energy_bpm1_stdev) +print(pulse_energy_bpm2, pulse_energy_bpm2_stdev) +caput(ENE_BPM1, pulse_energy_bpm1) +caput(ERR_BPM1, pulse_energy_bpm1_stdev) +caput(ENE_BPM2, pulse_energy_bpm2) +caput(ERR_BPM2, pulse_energy_bpm2_stdev) \ No newline at end of file diff --git a/script/Undulators/K_AR_KtoTaper.py b/script/Undulators/K_AR_KtoTaper.py new file mode 100644 index 0000000..81607b6 --- /dev/null +++ b/script/Undulators/K_AR_KtoTaper.py @@ -0,0 +1,37 @@ +import_py("CPython/k_fit", "k_fit") + +undlist = ("SARUN03","SARUN04","SARUN05","SARUN06","SARUN07","SARUN08","SARUN09", + "SARUN10","SARUN11","SARUN12","SARUN13","SARUN14","SARUN15") + +arr_k_total = [] +for und in undlist: + arr_k_total.append(caget(und + "-UIND030:K_UND_SET")) +i = 0 +while abs(arr_k_total[i] - arr_k_total[i + 1]) > 0.05: + i = i + 1 +lin_start = i +lin_fit, qua_fit, qua_start_fit = k_fit(arr_k_total[lin_start:]) +lin = int(round(lin_fit / 1e-6)) +qua = int(round(qua_fit / 1e-6)) +lin_start = int(lin_start) +lin_stop = len(arr_k_total) - 1 +qua_start = int(qua_start_fit) +qua_stop = len(arr_k_total) - 1 +caput("SARUN:TAPER-LIN", lin) +caput("SARUN:TAPER-QUA", qua) +caput("SARUN:TAPER-LIN-START", lin_start) +caput("SARUN:TAPER-LIN-STOP", lin_stop) +caput("SARUN:TAPER-QUA-START", qua_start) +caput("SARUN:TAPER-QUA-STOP", qua_stop) +u, i, j = 0, 0, 0 +for und in undlist: + K_taper = lin_fit * i + qua_fit * j**2 + k_total = arr_k_total[u] + K_set = k_total - K_taper + caputq(und + "-UIND030:K_TAPER_SET", K_taper) + caputq(und + "-UIND030:K_SET", K_set) + if lin_start <= u <= lin_stop: i = i + 1 + if qua_start <= u <= qua_stop: j = j + 1 + u = u + 1 + +set_return("Success") diff --git a/script/Undulators/K_AR_lasing_off.py b/script/Undulators/K_AR_lasing_off.py index 38d42e2..acc39fb 100644 --- a/script/Undulators/K_AR_lasing_off.py +++ b/script/Undulators/K_AR_lasing_off.py @@ -4,12 +4,12 @@ undlist = ("SARUN03","SARUN04","SARUN05","SARUN06","SARUN07","SARUN08","SARUN09" i = 0 amp = 0.10 for und in undlist: - rand = random() * 0.7 + 0.3 + rand = random() * 0.7 + 0.3 # 0.3 K_max: K_taper = -K_taper if K + K_taper < K_min: diff --git a/script/Undulators/K_AR_taper.py b/script/Undulators/K_AR_taper.py index 1ef8ff4..5499a5b 100644 --- a/script/Undulators/K_AR_taper.py +++ b/script/Undulators/K_AR_taper.py @@ -1,4 +1,3 @@ -print "ENTER" taper_lin = caget("SARUN:TAPER-LIN") * 1e-6 taper_qua = caget("SARUN:TAPER-QUA") * 1e-6 taper_lin_start = caget("SARUN:TAPER-LIN-START.RVAL") diff --git a/script/Undulators/K_AT_KtoTaper.py b/script/Undulators/K_AT_KtoTaper.py new file mode 100644 index 0000000..5ec477c --- /dev/null +++ b/script/Undulators/K_AT_KtoTaper.py @@ -0,0 +1,37 @@ +import_py("CPython/k_fit", "k_fit") + +undlist = ("SATUN06","SATUN07","SATUN08","SATUN09","SATUN10","SATUN11","SATUN12","SATUN13", + "SATUN15","SATUN16","SATUN17","SATUN18","SATUN19","SATUN20","SATUN21","SATUN22") + +arr_k_total = [] +for und in undlist: + arr_k_total.append(caget(und + "-UIND030:K_UND_SET")) +i = 0 +while abs(arr_k_total[i] - arr_k_total[i + 1]) > 0.05: + i = i + 1 +lin_start = i +lin_fit, qua_fit, qua_start_fit = k_fit(arr_k_total[lin_start:]) +lin = int(round(lin_fit / 1e-6)) +qua = int(round(qua_fit / 1e-6)) +lin_start = int(lin_start) +lin_stop = len(arr_k_total) - 1 +qua_start = int(qua_start_fit) +qua_stop = len(arr_k_total) - 1 +caput("SATUN:TAPER-LIN", lin) +caput("SATUN:TAPER-QUA", qua) +caput("SATUN:TAPER-LIN-START", lin_start) +caput("SATUN:TAPER-LIN-STOP", lin_stop) +caput("SATUN:TAPER-QUA-START", qua_start) +caput("SATUN:TAPER-QUA-STOP", qua_stop) +u, i, j = 0, 0, 0 +for und in undlist: + K_taper = lin_fit * i + qua_fit * j**2 + k_total = arr_k_total[u] + K_set = k_total - K_taper + caputq(und + "-UIND030:K_TAPER_SET", K_taper) + caputq(und + "-UIND030:K_SET", K_set) + if lin_start <= u <= lin_stop: i = i + 1 + if qua_start <= u <= qua_stop: j = j + 1 + u = u + 1 + +set_return("Success") diff --git a/script/Undulators/K_AT_color1_lasing_off.py b/script/Undulators/K_AT_color1_lasing_off.py index a3b84b8..907a59d 100644 --- a/script/Undulators/K_AT_color1_lasing_off.py +++ b/script/Undulators/K_AT_color1_lasing_off.py @@ -8,8 +8,8 @@ for und in undlist: K_taper = (-1)**i * 0.25 + random() * 0.050 - 0.025 i = i + 1 K = caget(und + "-UIND030:K_SET") - K_min = caget(und + "-UIND030:K_SET.DRVL") - K_max = caget(und + "-UIND030:K_SET.DRVH") + K_min = caget(und + "-UIND030:K_UND_SET.LOW") + K_max = caget(und + "-UIND030:K_UND_SET.HIGH") if K + K_taper > K_max: K_taper = K_max - K - random() * 0.025 if K + K_taper < K_min: diff --git a/script/Undulators/K_AT_color2_lasing_off.py b/script/Undulators/K_AT_color2_lasing_off.py index 950d445..78202c7 100644 --- a/script/Undulators/K_AT_color2_lasing_off.py +++ b/script/Undulators/K_AT_color2_lasing_off.py @@ -8,8 +8,8 @@ for und in undlist: K_taper = (-1)**i * 0.25 + random() * 0.050 - 0.025 i = i + 1 K = caget(und + "-UIND030:K_SET") - K_min = caget(und + "-UIND030:K_SET.DRVL") - K_max = caget(und + "-UIND030:K_SET.DRVH") + K_min = caget(und + "-UIND030:K_UND_SET.LOW") + K_max = caget(und + "-UIND030:K_UND_SET.HIGH") if K + K_taper > K_max: K_taper = K_max - K - random() * 0.025 if K + K_taper < K_min: diff --git a/script/Undulators/K_AT_lasing_off.py b/script/Undulators/K_AT_lasing_off.py index c1ffeee..79e4501 100644 --- a/script/Undulators/K_AT_lasing_off.py +++ b/script/Undulators/K_AT_lasing_off.py @@ -10,8 +10,8 @@ for und in undlist: K_taper = (-1)**i * amp * rand i = i + 1 K = caget(und + "-UIND030:K_SET") - K_min = caget(und + "-UIND030:K_SET.DRVL") - K_max = caget(und + "-UIND030:K_SET.DRVH") + K_min = caget(und + "-UIND030:K_UND_SET.LOW") + K_max = caget(und + "-UIND030:K_UND_SET.HIGH") if K + K_taper > K_max: K_taper = -K_taper if K + K_taper < K_min: diff --git a/script/Undulators/K_AT_taper.py b/script/Undulators/K_AT_taper.py index aa64a80..6950ac3 100644 --- a/script/Undulators/K_AT_taper.py +++ b/script/Undulators/K_AT_taper.py @@ -8,6 +8,10 @@ taper_qua_stop = caget("SATUN:TAPER-QUA-STOP.RVAL") undlist = ("SATUN06","SATUN07","SATUN08","SATUN09","SATUN10","SATUN11","SATUN12","SATUN13", "SATUN15","SATUN16","SATUN17","SATUN18","SATUN19","SATUN20","SATUN21","SATUN22") +screen_pos = caget("SATBD01-DSCR120:GET_SCREEN1_POS") +if screen_pos != "Out of beam": + caput("SATBD01-DSCR120:SET_SCREEN1_POS", 0) + u = 0 i, j = 0, 0 for und in undlist: diff --git a/script/Undulators/K_AT_taper1.py b/script/Undulators/K_AT_taper1.py index b7969d4..d26f8c5 100644 --- a/script/Undulators/K_AT_taper1.py +++ b/script/Undulators/K_AT_taper1.py @@ -8,6 +8,10 @@ taper_qua_stop = caget("SATUN:TAPER-QUA-STOP.RVAL") undlist = ("SATUN06","SATUN07","SATUN08","SATUN09","SATUN10","SATUN11","SATUN12","SATUN13", "SATUN15","SATUN16","SATUN17","SATUN18","SATUN19","SATUN20","SATUN21","SATUN22") +screen_pos = caget("SATBD01-DSCR120:GET_SCREEN1_POS") +if screen_pos != "Out of beam": + caput("SATBD01-DSCR120:SET_SCREEN1_POS", 0) + u = 0 i, j = 0, 0 for und in undlist: diff --git a/script/Undulators/K_AT_taper2.py b/script/Undulators/K_AT_taper2.py index 5168e66..6020eae 100644 --- a/script/Undulators/K_AT_taper2.py +++ b/script/Undulators/K_AT_taper2.py @@ -8,6 +8,10 @@ taper_qua_stop = caget("SATUN:TAPER-QUA-STOP.RVAL") undlist = ("SATUN06","SATUN07","SATUN08","SATUN09","SATUN10","SATUN11","SATUN12","SATUN13", "SATUN15","SATUN16","SATUN17","SATUN18","SATUN19","SATUN20","SATUN21","SATUN22") +screen_pos = caget("SATBD01-DSCR120:GET_SCREEN1_POS") +if screen_pos != "Out of beam": + caput("SATBD01-DSCR120:SET_SCREEN1_POS", 0) + u = 0 i, j = 0, 0 for und in undlist: diff --git a/script/Undulators/und_scan.py b/script/Undulators/und_scan.py index fc80d61..dc5cee8 100644 --- a/script/Undulators/und_scan.py +++ b/script/Undulators/und_scan.py @@ -1,42 +1,36 @@ -import ch.psi.pshell.epics.Positioner as Positioner -import ch.psi.pshell.epics.ChannelDouble as ChannelDouble +import ch.psi.pshell.epics.Positioner as Positioner +import ch.psi.pshell.epics.ChannelDouble as ChannelDouble import_py("CPython/hfitoff", "hfitoff") import_py("CPython/extremum", "extremum") - dry_run = False -do_elog = False - +do_elog = True +#und = "SARUN15" +#scan = "AR_K" if get_exec_pars().args: # args is set by callin process (Qt panel) und = args[0] scan = args[1] - if dry_run: und = "STEST01" scan = "AR_PHI" - -if scan == "AR_K" or scan == "AT_K": - x_channel = und + "-UIND030:K_SET" - message_channel = und + ":K-SCAN-MESSAGE" - x0 = caget(x_channel) - start = x0 - 0.005 - end = x0 + 0.005 - step = 10 - lat = 0.1 - nb = 90 -if scan == "AR_PHI" or scan == "AT_PHI": - message_channel = und + ":PHI-SCAN-MESSAGE" - start = -180 - end = 180 - step = 12 - lat = 0.1 - nb = 90 - -if scan == "AR_K": - x_ok_channel = und + "-UPHS060:GAP-POS-OK" # UPHS is slower +gd_state_init = {} +if scan == "AR_K": + gd_state_init["SARFE10-PBPG050:ENERGY-SELECT"] = caget("SARFE10-PBPG050:ENERGY-SELECT") + gd_state_init["SARFE10-PBPG050:ENERGY"] = caget("SARFE10-PBPG050:ENERGY") + machine_ene = caget("SARUN:FELPHOTENE") + caput("SARFE10-PBPG050:ENERGY", machine_ene * 1000) + caput("SARFE10-PBPG050:ENERGY-SELECT", "USER") + x_channel = und + "-UIND030:K_SET" # use UPHS for pos ok -> UPHS slower (exception for SARUN15) + x_ok_channel = und + "-UPHS060:GAP-POS-OK" if und is not "SARUN15" else "SARUN15-UIND030:GAP-POS-OK" y_channel = "SARFE10-PBIG050-EVR0:CALCI" elif scan == "AT_K": + gd_state_init["SATFE10-PEPG046:ENERGY-SELECT"] = caget("SATFE10-PEPG046:ENERGY-SELECT") + gd_state_init["SATFE10-PEPG046:ENERGY"] = caget("SATFE10-PEPG046:ENERGY") + machine_ene = caget("SATUN:FELPHOTENE") + caput("SATFE10-PEPG046:ENERGY", machine_ene * 1000) + caput("SATFE10-PEPG046:ENERGY-SELECT", "USER") + x_channel = und + "-UIND030:K_SET" x_ok_channel = und + "-UIND030:RADIAL-POS-OK" y_channel = "SATFE10-PEPG046-EVR0:CALCI" elif scan == "AR_PHI": @@ -47,11 +41,30 @@ elif scan == "AT_PHI": x_channel = und + "-UDLY060:PH-SHIFT-OP" x_ok_channel = und + "-UDLY060:GAP-COMP-OP" y_channel = "SATFE10-PEPG046-EVR0:CALCI" - if und == "STEST01" and scan == "AR_K": y_channel = "STEST01:K-CALCI" if und == "STEST01" and scan == "AR_PHI": y_channel = "STEST01:PHI-CALCI" +if scan == "AR_K" or scan == "AT_K": + message_channel = und + ":K-SCAN-MESSAGE" + x0 = caget(x_channel) + start = x0 - 0.005 + end = x0 + 0.005 + step = 10 + lat = 0.02 + nb = 150 +if scan == "AR_PHI" or scan == "AT_PHI": + message_channel = und + ":PHI-SCAN-MESSAGE" + start = -180 + end = 180 + step = 12 + lat = 0.02 + nb = 150 +if scan == "AR_K" or scan == "AR_PHI": + gd_state_init["SARFE10-PBPG050:HAMP-X-HVS-STATUS"] = caget("SARFE10-PBPG050:HAMP-X-HVS-STATUS") + gd_state_init["SARFE10-PBPG050:HAMP-Y-HVS-STATUS"] = caget("SARFE10-PBPG050:HAMP-Y-HVS-STATUS") + caput("SARFE10-PBPG050:HAMP-X-HVS-STATUS", "OFF") + caput("SARFE10-PBPG050:HAMP-Y-HVS-STATUS", "OFF") x_val = ChannelDouble(x_channel, x_channel) x_val.initialize() @@ -60,37 +73,56 @@ y_val.initialize() x_val0 = x_val.read() y_averager = create_averager(y_val, nb, lat) -#check mover position +# pause scan when beam is down +def is_beam_ok(): + mps_ma = int(caget("SIN-EMED-DTSA001:LEVEL1_MA.RVAL")) + mps_ar = int(caget("SIN-EMED-DTSA002:LEVEL1_AR.RVAL")) + mps_at = int(caget("SIN-EMED-DTSA003:LEVEL1_AT.RVAL")) + beam_ok = (mps_ma + mps_ar + mps_at == 3) + return beam_ok + +def wait_beam(): + if not is_beam_ok(): + print("Waiting for beam...") + while not is_beam_ok(): + time.sleep(0.5) + print("Beam ok") + +# check mover position and wait for beam def before(): time.sleep(1.0) - timeout = 10.0 + timeout = 15.0 start_time = time.time() while (True): mover_status = caget(x_ok_channel) - print(mover_status) if mover_status=="OK" or mover_status=="True": break if time.time() - start_time > timeout: raise Exception("mover timeout") + wait_beam() -#update the plot dynamically +# check for beam and update the plot dynamically arr_x, arr_y = [],[] def after(rec): - arr_x.append(rec.positions[0]) - arr_y.append(rec.readables[0].mean) - caput("SF-SCAN-GLOBAL:X-ARRAY", to_array(arr_x, 'd')) - caput("SF-SCAN-GLOBAL:Y-ARRAY", to_array(arr_y, 'd')) + if not is_beam_ok(): + print("Beam is down, invalidating record...") + rec.invalidate() + arr_x.append(rec.positions[0]) + arr_y.append(rec.readables[0].mean) + caput("SF-SCAN-GLOBAL:X-ARRAY", to_array(arr_x, 'd')) + caput("SF-SCAN-GLOBAL:Y-ARRAY", to_array(arr_y, 'd')) -#scan and plot +# scan and plot try: - caput("SF-SCAN-GLOBAL:FIT-X-ARRAY", to_array([0.0], 'd')) - caput("SF-SCAN-GLOBAL:FIT-Y-ARRAY", to_array([0.0], 'd')) x_val.write(start) time.sleep(5.0) - caput(message_channel, "scanning ") + caput(message_channel, "scanning...") + caput("SF-SCAN-GLOBAL:FIT-X-ARRAY", to_array([0.0], 'd')) + caput("SF-SCAN-GLOBAL:FIT-Y-ARRAY", to_array([0.0], 'd')) r = lscan(x_val, y_averager, start, end, step, latency=lat, before_read = before, after_read = after) x_array = r.getPositions(0) - y_array = energy = [val.mean for val in r.getReadable(0)] + y_array = [val.mean for val in r.getReadable(0)] + y_array_error_mean = mean([val.stdev for val in r.getReadable(0)]) caput("SF-SCAN-GLOBAL:X-ARRAY", to_array(x_array, 'd')) caput("SF-SCAN-GLOBAL:Y-ARRAY", to_array(y_array, 'd')) try: @@ -98,6 +130,10 @@ try: x_max, y_max, fit_x, fit_y, R2 = extremum(x_array, y_array) if scan == "AR_PHI" or scan == "AT_PHI": fit_amplitude, fit_x_deg, fit_offset, x_max, fit_x, fit_y = hfitoff(y_array, x_array) + while x_max < -180: + x_max = x_max + 360 + while x_max > 180: + x_max = x_max - 360 except: raise Exception("Fit failure") plt = plot(None, name="param scan")[0] @@ -111,11 +147,42 @@ try: caput(und + ":SCAN-CREST", x_max) caput("SF-SCAN-GLOBAL:FIT-X-ARRAY", fit_x) caput("SF-SCAN-GLOBAL:FIT-Y-ARRAY", fit_y) + signal_amplitude = max(fit_y) - min(fit_y) + signal_to_noise = signal_amplitude / y_array_error_mean if y_array_error_mean != 0 else 0 + now = str(caget("SF-TIME:FULL-DATE")) + now = now[:16] if now[0].isdigit() else "" + message = now if scan == "AR_K" or scan == "AT_K": - caput(message_channel, "on-crest: " + ("%.4f" % x_max)) + message = message + (" %.4f" % x_max) if scan == "AR_PHI" or scan == "AT_PHI": - caput(message_channel, "on-crest: " + ("%.1f" % x_max)) + message = message + (" %.1f deg" % x_max) + message = message + " (snr: " + ("%.2f)" % signal_to_noise) + caput(message_channel, message) finally: + if scan == "AR_K": + caput("SARFE10-PBPG050:ENERGY", gd_state_init["SARFE10-PBPG050:ENERGY"]) + caput("SARFE10-PBPG050:ENERGY-SELECT", gd_state_init["SARFE10-PBPG050:ENERGY-SELECT"]) + if scan == "AT_K": + caput("SATFE10-PEPG046:ENERGY", gd_state_init["SATFE10-PEPG046:ENERGY"]) + caput("SATFE10-PEPG046:ENERGY-SELECT", gd_state_init["SATFE10-PEPG046:ENERGY-SELECT"]) + if scan == "AR_K" or scan == "AR_PHI": + caput("SARFE10-PBPG050:HAMP-X-HVS-STATUS", gd_state_init["SARFE10-PBPG050:HAMP-X-HVS-STATUS"]) + caput("SARFE10-PBPG050:HAMP-Y-HVS-STATUS", gd_state_init["SARFE10-PBPG050:HAMP-Y-HVS-STATUS"]) x_val.write(x_val0) x_val.close() y_val.close() + +# Elog entry +if do_elog: + title = "Undulator scan " + und + log_msg = "Data file: " + get_exec_pars().path + "\n" + if scan == "AR_K" or scan == "AT_K": + log_msg = log_msg + "On-crest K: %0.4f" % x_max + "\n" + if scan == "AR_PHI" or scan == "AT_PHI": + log_msg = log_msg + "On-crest phase: %0.1f" % x_max + " deg\n" + log_msg = log_msg + "Scan quality: %0.2f" % signal_to_noise + attachments = get_plot_snapshots(size=(600,400)) + elog(title, log_msg, attachments) + +set_return([x_max, signal_to_noise]) + diff --git a/script/Undulators/und_scan_global.py b/script/Undulators/und_scan_global.py index 916d312..b38658e 100644 --- a/script/Undulators/und_scan_global.py +++ b/script/Undulators/und_scan_global.py @@ -1,9 +1,41 @@ -und_table = ["SARUN03", "SARUN04", "SARUN05", "SARUN06", "SARUN07", - "SARUN08", "SARUN09", "SARUN10", "SARUN11", "SARUN12", - "SARUN13", "SARUN13", "SARUN13", "STEST01"] +und_table = ["SARUN03", "SARUN04", "SARUN05", "SARUN06", "SARUN07", + "SARUN08", "SARUN09", "SARUN10", "SARUN11", "SARUN12", + "SARUN13", "SARUN14", "SARUN15", "STEST01", "SATUN06", + "SATUN07", "SATUN08", "SATUN09", "SATUN10", "SATUN11", + "SATUN12", "SATUN13", "SATUN15", "SATUN16", "SATUN17", + "SATUN18", "SATUN19", "SATUN20", "SATUN21", "SATUN22"] +psh_table = ["SARUN03", "SARUN04", "SARUN05", "SARUN06", "SARUN07", + "SARUN08", "SARUN09", "SARUN10", "SARUN11", "SARUN12", + "SARUN13", "SARUN14", "STEST01", "SATUN06", + "SATUN07", "SATUN08", "SATUN09", "SATUN10", "SATUN11", + "SATUN12", "SATUN13", "SATUN15", "SATUN16", "SATUN17", + "SATUN18", "SATUN19", "SATUN20", "SATUN21"] +snr_threshold = caget("SF-SCAN-GLOBAL:SNR-THR") -for und in und_table: - req = caget(und + "-RSYS:PHASE-SCAN-REQUIRED") - if req == "True": - run("Undulators/und_scan.py") - caput(und + ":PHASE-SCAN-REQUIRED", 0) +und_scan_global_state.assertReady() +und_scan_global_state = State.Busy +und_scan_global_result = None +try: + for und in und_table: + req = caget(und + ":K-SCAN-REQUIRED") + if req == "True": + scan = "AT_K" if und.startswith("SAT") else "AR_K" + [max_val, snr] = run("Undulators/und_scan.py") + if snr > snr_threshold: + run("Undulators/und_scan_set.py") + caput(und + ":K-SCAN-REQUIRED", 0) + for und in psh_table: + req = caget(und + ":PHI-SCAN-REQUIRED") + if req == "True": + scan = "AT_PHI" if und.startswith("SAT") else "AR_PHI" + [max_val, snr] = run("Undulators/und_scan.py") + if snr > snr_threshold: + run("Undulators/und_scan_set.py") + caput(und + ":PHI-SCAN-REQUIRED", 0) + set_return('Success') + und_scan_global_result = "Ok" +except: + und_scan_global_result = str(sys.exc_info()[1]) +finally: + und_scan_global_state = State.Ready + \ No newline at end of file diff --git a/script/Undulators/und_scan_set.py b/script/Undulators/und_scan_set.py index 5436a5a..852c1b8 100644 --- a/script/Undulators/und_scan_set.py +++ b/script/Undulators/und_scan_set.py @@ -1,7 +1,7 @@ if get_exec_pars().args: # args is set by callin process (Qt panel) und = args[0] scan = args[1] - + if scan == "AR_K": set_channel = und + "-UIND030:K_SET" elif scan == "AR_PHI": @@ -14,3 +14,5 @@ elif scan == "AT_PHI": set_value = caget(und + ":SCAN-CREST") caput(set_channel, set_value) +set_return([set_channel, set_value]) + diff --git a/script/local.py b/script/local.py old mode 100755 new mode 100644 index d1b6e1d..7ecb96a --- a/script/local.py +++ b/script/local.py @@ -1,149 +1,182 @@ ################################################################################################### # Deployment specific global definitions - executed after startup.py ################################################################################################### - + from mathutils import estimate_peak_indexes, fit_gaussians, create_fit_point_list, Gaussian from mathutils import fit_polynomial,fit_gaussian, fit_harmonic, calculate_peaks from mathutils import PolynomialFunction, Gaussian, HarmonicOscillator import java.awt.Color as Color - -try: - from jeputils import import_py -except: - pass - -run("Devices/Elements") - -################################################################################################### -# Layout setup -################################################################################################### -import ch.psi.pshell.data.LayoutSF as LayoutSF - -LayoutSF.setExperimentArguments([charge, laser, rep_rate_bunch_1, rep_rate_bunch_2, destination_AR, energy_AR]) - - - -################################################################################################### -# Machine utilities -################################################################################################### - - -LASER_SETTLING_TIME = 3.0 - -def laser_on(bunch=None): - print "Laser On - bunch “ + str(bunch) - #caput("SIN-TIMAST-TMA:Beam-Las-Delay-Sel", 0) - if (bunch==1) or (bunch is None): - caput("SWISSFEL-STATUS:Bunch-1-OnDelay-Sel", 0) - if (bunch==2) or (bunch is None): - caput("SWISSFEL-STATUS:Bunch-2-OnDelay-Sel", 0) - caput("SIN-TIMAST-TMA:Beam-Apply-Cmd.PROC", 1) - time.sleep(LASER_SETTLING_TIME) - -def laser_off(bunch=None): - print "Laser Off - bunch “ + str(bunch) - #caput("SIN-TIMAST-TMA:Beam-Las-Delay-Sel", 1) - if (bunch==1) or (bunch is None): - caput("SWISSFEL-STATUS:Bunch-1-OnDelay-Sel", 1) - if (bunch==2) or (bunch is None): - caput("SWISSFEL-STATUS:Bunch-2-OnDelay-Sel", 1) - caput("SIN-TIMAST-TMA:Beam-Apply-Cmd.PROC", 1) - time.sleep(LASER_SETTLING_TIME) - -def is_laser_on(bunch=None): - #return (caget ("SIN-TIMAST-TMA:Beam-Las-Delay-Sel",'d') == 0 ) - if bunch==1: - return (caget ("SWISSFEL-STATUS:Bunch-1-OnDelay-Sel",'d') == 0 ) - if bunch==2: - return (caget ("SWISSFEL-STATUS:Bunch-2-OnDelay-Sel",'d') == 0 ) - if bunch is None: - return is_laser_on(1) and is_laser_on(2) - -def save_laser_state(): - global laser_was_on_1, laser_was_on_2 - laser_was_on_1 = is_laser_on(1) - laser_was_on_2 = is_laser_on(2) - -def restore_laser_state(): - global laser_was_on_1, laser_was_on_2 - if laser_was_on_1: - laser_on(1) - else: - laser_off(1) - if laser_was_on_2: - laser_on(2) - else: - laser_off(2) - - -# Switch off magnets -def ccr(magnet): - while caget(magnet+ ":I-COMP") > 0: - sleep(0.5) - -def switch_off_magnets(magnets = None): - if magnets is None: - magnets = [ "SINEG01-MCRX120","SINEG01-MCRY120", - "SINEG01-MQUA140", - "SINEG01-MQSK150", - "SINEG01-MCRX160","SINEG01-MCRY160", - "SINEG01-MCRX180","SINEG01-MCRY180", - "SINEG01-MCRX200","SINEG01-MCRY200", - "SINEG01-MCRX220","SINEG01-MCRY220", - "SINEG01-MQUA310", - "SINEG01-MQSK320" ] - magnets = to_list(magnets) - for m in magnets: - caput(m + ":I-SET", 0.0) - sleep(0.5) - for m in magnets: - ccr(m) - -def is_timing_ok(): - return caget("SIN-TIMAST-TMA:SOS-COUNT-CHECK") == 0 - -def get_repetition_rate(bunch=1, setp=None): - if not setp: - ret = caget(get_repetition_rate_rb_channel(bunch), 'd') - if setp==False or ret > 0: - return ret - print "Readback is 0: returning Setpoint" - sel = caget("SIN-TIMAST-TMA:Bunch-" + str(bunch) + "-Freq-Sel") - return float(sel.split(" ")[0]) - - -def get_repetition_rate_rb_channel(bunch=1): - if bunch==2: - return "SIN-TIMAST-TMA:Bunch-2-Appl-Freq-RB" - else: - return "SIN-TIMAST-TMA:Bunch-1-Appl-Freq-RB" - -def ws_status(): - """ - Display status of all wire scanners - """ - run("Diagnostics/WireScannersStatus") - - -def get_beam_ok_channel(bunch): - if bunch==2: - return "SIN-CVME-TIFGUN-EVR0:BUNCH-2-OK" - if bunch==1: - return "SIN-CVME-TIFGUN-EVR0:BUNCH-1-OK" - -################################################################################################### -# Maths utilities -################################################################################################### - + +try: + from jeputils import import_py +except: + pass + +run("Devices/Elements") + +################################################################################################### +# Layout setup +################################################################################################### +import ch.psi.pshell.data.LayoutSF as LayoutSF + +LayoutSF.setExperimentArguments([charge, laser, rep_rate_bunch_1, rep_rate_bunch_2, destination_AR, energy_AR]) + + + +################################################################################################### +# Machine utilities +################################################################################################### + + +LASER_SETTLING_TIME = 3.0 + +def laser_on(bunch=None): + print "Laser On - bunch “ + str(bunch) + #caput("SIN-TIMAST-TMA:Beam-Las-Delay-Sel", 0) + if (bunch==1) or (bunch is None): + caput("SWISSFEL-STATUS:Bunch-1-OnDelay-Sel", 0) + if (bunch==2) or (bunch is None): + caput("SWISSFEL-STATUS:Bunch-2-OnDelay-Sel", 0) + caput("SIN-TIMAST-TMA:Beam-Apply-Cmd.PROC", 1) + time.sleep(LASER_SETTLING_TIME) + +def laser_off(bunch=None): + print "Laser Off - bunch “ + str(bunch) + #caput("SIN-TIMAST-TMA:Beam-Las-Delay-Sel", 1) + if (bunch==1) or (bunch is None): + caput("SWISSFEL-STATUS:Bunch-1-OnDelay-Sel", 1) + if (bunch==2) or (bunch is None): + caput("SWISSFEL-STATUS:Bunch-2-OnDelay-Sel", 1) + caput("SIN-TIMAST-TMA:Beam-Apply-Cmd.PROC", 1) + time.sleep(LASER_SETTLING_TIME) + +def is_laser_on(bunch=None): + #return (caget ("SIN-TIMAST-TMA:Beam-Las-Delay-Sel",'d') == 0 ) + if bunch==1: + return (caget ("SWISSFEL-STATUS:Bunch-1-OnDelay-Sel",'d') == 0 ) + if bunch==2: + return (caget ("SWISSFEL-STATUS:Bunch-2-OnDelay-Sel",'d') == 0 ) + if bunch is None: + return is_laser_on(1) and is_laser_on(2) + +def save_laser_state(): + global laser_was_on_1, laser_was_on_2 + laser_was_on_1 = is_laser_on(1) + laser_was_on_2 = is_laser_on(2) + +def restore_laser_state(): + global laser_was_on_1, laser_was_on_2 + if laser_was_on_1: + laser_on(1) + else: + laser_off(1) + if laser_was_on_2: + laser_on(2) + else: + laser_off(2) + +#Wire scanners +def is_blm_enabled(name, bunch=None): + ch1 = name+":B1_ROI_ACTIVE_OP" + ch2 = name+":B2_ROI_ACTIVE_OP" + if bunch is None: + return (is_blm_enabled(name, 1), is_blm_enabled(name, 2)) + try: + if (bunch==1): + if caget(ch1, 'i'): + return True + elif (bunch==2): + if caget(ch2, 'i'): + return True + except: + msg = "Error reading blm " + str(name) + " enabled bunch=" + str( bunch) + print msg + log(msg) + return False + +def set_blm_enabled(value, name, bunch=None): + try: + if type(value) is tuple: + caput(name+":B1_ROI_ACTIVE_OP", value[0]) + caput(name+":B2_ROI_ACTIVE_OP", value[0]) + else: + if (bunch==1) or (bunch is None): + caput(name+":B1_ROI_ACTIVE_OP", value) + if (bunch==2) or (bunch is None): + caput(name+":B2_ROI_ACTIVE_OP", value) + except: + msg = "Error setting blm " + str(name) + " enabled=" + str(value) + " bunch=" + str( bunch) + print msg + log(msg) + +# Switch off magnets +def ccr(magnet): + while caget(magnet+ ":I-COMP") > 0: + sleep(0.5) + +def switch_off_magnets(magnets = None): + if magnets is None: + magnets = [ "SINEG01-MCRX120","SINEG01-MCRY120", + "SINEG01-MQUA140", + "SINEG01-MQSK150", + "SINEG01-MCRX160","SINEG01-MCRY160", + "SINEG01-MCRX180","SINEG01-MCRY180", + "SINEG01-MCRX200","SINEG01-MCRY200", + "SINEG01-MCRX220","SINEG01-MCRY220", + "SINEG01-MQUA310", + "SINEG01-MQSK320" ] + magnets = to_list(magnets) + for m in magnets: + caput(m + ":I-SET", 0.0) + sleep(0.5) + for m in magnets: + ccr(m) + +def is_timing_ok(): + return caget("SIN-TIMAST-TMA:SOS-COUNT-CHECK") == 0 + +def get_repetition_rate(bunch=1, setp=None): + if not setp: + ret = caget(get_repetition_rate_rb_channel(bunch), 'd') + if setp==False or ret > 0: + return ret + print "Readback is 0: returning Setpoint" + sel = caget("SIN-TIMAST-TMA:Bunch-" + str(bunch) + "-Freq-Sel") + return float(sel.split(" ")[0]) + + +def get_repetition_rate_rb_channel(bunch=1): + if bunch==2: + return "SIN-TIMAST-TMA:Bunch-2-Appl-Freq-RB" + else: + return "SIN-TIMAST-TMA:Bunch-1-Appl-Freq-RB" + +def ws_status(): + """ + Display status of all wire scanners + """ + run("Diagnostics/WireScannersStatus") + + +def get_beam_ok_channel(bunch): + if bunch==2: + return "SIN-CVME-TIFGUN-EVR0:BUNCH-2-OK" + if bunch==1: + return "SIN-CVME-TIFGUN-EVR0:BUNCH-1-OK" + +################################################################################################### +# Maths utilities +################################################################################################### + def fit(ydata, xdata = None): """ Gaussian fit """ if xdata is None: xdata = frange(0, len(ydata), 1) - #ydata = to_list(ydata) - #xdata = to_list(xdata) + #ydata = to_list(ydata) + #xdata = to_list(xdata) max_y= max(ydata) index_max = ydata.index(max_y) max_x= xdata[index_max] @@ -219,67 +252,67 @@ def hfit(ydata, xdata = None): print "max = ",max_x p.addMarker(max_x, None, "Max="+str(round(max_x ,2)), Color.MAGENTA.darker()) return (amplitude, angular_frequency, phase, False, max_x, fit_x, fit_y) - -def clear_convex_hull_plot(title): - plots = get_plots(title = title) - if len(plots)>0: - plots[0].clear() - -def add_convex_hull_plot(title, x,y, name=None, clear = False, x_range = None, y_range = None): - plots = get_plots(title = title) - p = None - if len(plots)==0: - p = plot(None,name=name, title = title)[0] - if x_range is not None: - p.getAxis(p.AxisId.X).setRange(x_range[0], x_range[1]) - if y_range is not None: - p.getAxis(p.AxisId.Y).setRange(y_range[0], y_range[1]) - p.setLegendVisible(True) - else: - p = plots[0] - if clear: - p.clear() - p.addSeries(LinePlotSeries(name)) - s = p.getSeries(name) - s.setLinesVisible(False) - s.setPointSize(3) - x, y = to_array(x,'d') , to_array(y,'d') - s.setData(x, y) - - #Convex Hull - #In the first time the plot shows, it takes some time for the color to be assigned - timeout = 0 - while s.color is None and timeout<1000: - time.sleep(0.001) - timeout = timeout + 1 - hull = LinePlotSeries(name + "Hull", s.color) - p.addSeries(hull) - #Bounding box - #x1,x2,y1,y2 = min(x), max(x), min(y), max(y) - #(hx,hy) = ([x1,x2, x2, x1, x1], [y1, y1, y2, y2, y1]) - (hx,hy) = convex_hull(x=x, y=y) - hx.append(hx[0]); hy.append(hy[0]) - hull.setLineWidth(2) - hull.setData(to_array(hx,'d') , to_array(hy,'d')) - hull.setColor(s.color) - return [hx,hy] - -################################################################################################### -# Tools -################################################################################################### - +def clear_convex_hull_plot(title): + plots = get_plots(title = title) + if len(plots)>0: + plots[0].clear() + +def add_convex_hull_plot(title, x,y, name=None, clear = False, x_range = None, y_range = None): + plots = get_plots(title = title) + p = None + if len(plots)==0: + p = plot(None,name=name, title = title)[0] + if x_range is not None: + p.getAxis(p.AxisId.X).setRange(x_range[0], x_range[1]) + if y_range is not None: + p.getAxis(p.AxisId.Y).setRange(y_range[0], y_range[1]) + p.setLegendVisible(True) + else: + p = plots[0] + if clear: + p.clear() + p.addSeries(LinePlotSeries(name)) + s = p.getSeries(name) + s.setLinesVisible(False) + s.setPointSize(3) + x, y = to_array(x,'d') , to_array(y,'d') + s.setData(x, y) + + #Convex Hull + #In the first time the plot shows, it takes some time for the color to be assigned + timeout = 0 + while s.color is None and timeout<1000: + time.sleep(0.001) + timeout = timeout + 1 + hull = LinePlotSeries(name + "Hull", s.color) + p.addSeries(hull) + #Bounding box + #x1,x2,y1,y2 = min(x), max(x), min(y), max(y) + #(hx,hy) = ([x1,x2, x2, x1, x1], [y1, y1, y2, y2, y1]) + (hx,hy) = convex_hull(x=x, y=y) + hx.append(hx[0]); hy.append(hy[0]) + hull.setLineWidth(2) + hull.setData(to_array(hx,'d') , to_array(hy,'d')) + hull.setColor(s.color) + return [hx,hy] + + +################################################################################################### +# Tools +################################################################################################### + def elog(title, message, attachments = [], application = None, author = None, category = "Info", domain = "", logbook = "SwissFEL commissioning data", encoding=1): """ Add entry to ELOG. """ if author is None: author = "pshell" #get_context().user.name - - if application is None: - application = get_exec_pars().name - + + if application is None: + application = get_exec_pars().name + typ = "pshell" entry = "" @@ -290,7 +323,7 @@ def elog(title, message, attachments = [], application = None, author = None, ca cmd = cmd + '-a "Title=' + title + '" ' cmd = cmd + '-a "Category=' + category + '" ' cmd = cmd + '-a "Domain=' + domain + '" ' - cmd = cmd + '-a "Application=' + application + '" ' + cmd = cmd + '-a "Application=' + application + '" ' for attachment in attachments: cmd = cmd + '-f "' + attachment + '" ' cmd = cmd + '-n ' + str(encoding) @@ -304,217 +337,224 @@ def elog(title, message, attachments = [], application = None, author = None, ca if (err is not None) and err!="": raise Exception(err) print out - import ch.psi.pshell.ui.App as App - if not App.isOutputRedirected(): - import java.lang.System as System - System.out.println(out) - try: - return int(out[out.find("ID=") +3 : ]) - except: - print out - - -################################################################################################### -# Pseudo-devices -################################################################################################### -class Sinusoid(ReadonlyRegisterBase): - def doRead(self): - self.x = self.x + 5.0 if hasattr(self, 'x') else 0.0 - return math.sin(self.x * math.pi / 180.0) - -""" + import ch.psi.pshell.ui.App as App + if not App.isOutputRedirected(): + import java.lang.System as System + System.out.println(out) + try: + return int(out[out.find("ID=") +3 : ]) + except: + print out + + +################################################################################################### +# Pseudo-devices +################################################################################################### +class Sinusoid(ReadonlyRegisterBase): + def doRead(self): + self.x = self.x + 5.0 if hasattr(self, 'x') else 0.0 + return math.sin(self.x * math.pi / 180.0) + +""" add_device(Sinusoid("phase"), True) add_device(Sinusoid("bpm_q"), True) add_device(Sinusoid("center_x"), True) add_device(Sinusoid("center_y"), True) center_x.setPolling(100) -center_y.setPolling(100) - -import random -class ComX(ReadonlyRegisterBase): - def doRead(self): - ret = gun_solenoid.read()/10.0 + random.random() - print "X=",ret - return ret -class ComY(ReadonlyRegisterBase): - def doRead(self): - ret = gun_solenoid.read()/15.0 + random.random() - print "Y=",ret - return ret -comx = ComX(); comx.initialize() -comy = ComY(); comy.initialize() -avx = create_averager(comx, 5, 0.001) -avy = create_averager(comy, 5, 0.001) -""" - - -################################################################################################### -# Camera server -################################################################################################### -def wait_cam_server_message(number_messages = 1, timeout = 10000): - for i in range (number_messages): - if not cam_server.stream.waitCacheChange(timeout): - raise Exception("Timeout receiving from camera server") - -def get_cam_server_stats(number_images=1, async = True, interval=-1, good_region = False): - ret = [] - wait_cam_server_message() - prefix = "gr_" if good_region else "" - for ident in [prefix+"x_center_of_mass", prefix+"y_center_of_mass", prefix+"x_rms", prefix+"y_rms"]: - child = cam_server.stream.getChild(ident) - av = create_averager(child, number_images, interval) - av.monitored = async - ret.append(av) - return ret - -def wait_cam_server_background(background, timeout = 10000): - start = time.time() - while True: - processing_parameters = cam_server.getProcessingParameters() - if (processing_parameters is not None) and (str(background) == processing_parameters["image_background"]): - return - if (time.time()-start) > timeout/1000: - raise Exception("Timeout waiting for camera server background: " + str(background)) - time.sleep(0.01) - - -def get_camera_type(camera_name): - if "LCAM" in camera_name: return "LASER" - if "DSCR" in camera_name or \ - "DSRM" in camera_name or \ - "DLAC" in camera_name: return "ELECTRONS" - if "PROF" in camera_name or \ - "PPRM" in camera_name or \ - "PSSS" in camera_name or \ - "PSCR" in camera_name or \ - "PSRD" in camera_name: return "PHOTONICS" - return "UNKNOWN" - - -################################################################################################### -# Camera scans -################################################################################################### - -# source = "server", "camtool", "bpm" or "direct" -def setup_camera_scan(): - global source, camera_name, bpm_name, number_images, use_background, multiple_background, number_backgrounds, dry_run - if not is_laser_on(1) and not is_laser_on(2): - raise Exception("Both bunches are on delay") - save_laser_state() - multiple_background = use_background and multiple_background - if source == "server": - cam_server.start(camera_name + "_sp", use_screen_panel_stream) - if use_background: - if not dry_run: - laser_off() - bg=cam_server.captureBackground(1 if multiple_background else number_backgrounds) - cam_server.setBackgroundSubtraction(True) - if not multiple_background: wait_cam_server_background(bg) - else: - cam_server.setBackgroundSubtraction(False) - - elif source == "camtool": - #kill_camtool() - check_camtool() - if use_background: - if not dry_run: - laser_off() - if not multiple_background: - camtool.stop() - camtool.grabBackground(camera_name, number_backgrounds) - camtool.start(camera_name, 0, use_background, None, 0.0, None) - else: - if source == "bpm": - run("Devices/BpmStats") - add_device(BpmStats("image_stats", bpm_name), True) - multiple_background = False - use_background = False - else: - run("Devices/ImageStats") - add_device(ImageStats("image_stats", camera_name), True) - add_device(image_stats.source, True) - image_stats.enableBackground(use_background) - if use_background: - laser_off() - if not multiple_background: - image_stats.grabBackground(number_backgrounds) - image_stats.setNumberOfImages(max(number_images,1)) - - if not multiple_background: - if not dry_run: - #laser_on() - restore_laser_state() - -def before_sample_camera_scan(): - global source, camera_name, number_images, use_background, multiple_background, number_backgrounds, dry_run - if source == "server": - if multiple_background: - bg = cam_server.captureBackground(number_backgrounds) - wait_cam_server_background(bg) - if not dry_run: - #laser_on() - restore_laser_state() - wait_cam_server_message(number_images) - elif source == "camtool": - if multiple_background: - camtool.stop() - camtool.grabBackground(camera_name, number_backgrounds) - camtool.start(camera_name, 0, use_background, None, 0.0, None) - if not dry_run: - #laser_on() - restore_laser_state() - wait_camtool_message(number_images) #Wait filing the averager cache - else: - if multiple_background: - image_stats.grabBackground(number_backgrounds) - #laser_on() - restore_laser_state() - image_stats.update() - -def after_sample_camera_scan(): - if multiple_background: - if not dry_run: - laser_off() - -def get_camera_scan_sensors(): - global source, camera_name, number_images, use_background, multiple_background, number_backgrounds, dry_run - if source == "server": - sensors = get_cam_server_stats(number_images, good_region=use_good_region) - if plot_image: - sensors.append(cam_server.getDataMatrix()) - elif source == "camtool": - sensors = get_camtool_stats(number_images, good_region=use_good_region) - if plot_image: - sensors.append(camtool.getDataMatrix()) - else: - sensors = [image_stats.com_x_mean, image_stats.com_y_mean, image_stats.com_x_stdev, image_stats.com_y_stdev] - if plot_image and (source == "direct"): - sensors.append(image_stats.source.getDataMatrix()) - return sensors - -def end_camera_scan(): - global source, camera_name, number_images, use_background, multiple_background, number_backgrounds, dry_run - #if source == "server": cam_server.stop() - #elif source == "camtool": camtool.stop() - #elif source == "camtool": camtool.stop() - #else: image_stats.stop() - if not dry_run: - restore_laser_state() - -################################################################################################### -#CAS -################################################################################################### - -if get_context().isServerEnabled(): - #CAS.setServerPort(5062) - add_device(EpicsServerUrl("epics_server_url_old", "PSHELL_OP:SERVER_URL"), True) #TODO: Change dependencies to "SF-PSHELL_OP:SERVER_URL and remove - add_device(EpicsServerUrl("epics_server_url", "SF-PSHELL_OP:SERVER_URL"), True) - add_device(EpicsServerState("epics_server_state", "SF-PSHELL_OP:STATE"), True) - add_device(EpicsCmdAPI("epics_cmd", "SF-PSHELL_OP:CMD", as_string=False), True) - add_device(EpicsCmdAPI("epics_cmd_bg", "SF-PSHELL_OP:CMD_BG", as_string=False, background=True), True) - add_device(EpicsCmdAPI("epics_cmd_str", "SF-PSHELL_OP:CMD_STR", as_string=True), True) - add_device(EpicsCmdAPI("epics_cmd_str_bg", "SF-PSHELL_OP:CMD_STR_BG", as_string=True, background=True), True) - - - - +center_y.setPolling(100) + +import random +class ComX(ReadonlyRegisterBase): + def doRead(self): + ret = gun_solenoid.read()/10.0 + random.random() + print "X=",ret + return ret +class ComY(ReadonlyRegisterBase): + def doRead(self): + ret = gun_solenoid.read()/15.0 + random.random() + print "Y=",ret + return ret +comx = ComX(); comx.initialize() +comy = ComY(); comy.initialize() +avx = create_averager(comx, 5, 0.001) +avy = create_averager(comy, 5, 0.001) +""" + + +################################################################################################### +# Camera server +################################################################################################### +def wait_cam_server_message(number_messages = 1, timeout = 10000): + for i in range (number_messages): + if not cam_server.stream.waitCacheChange(timeout): + raise Exception("Timeout receiving from camera server") + +def get_cam_server_stats(number_images=1, async = True, interval=-1, good_region = False): + ret = [] + wait_cam_server_message() + prefix = "gr_" if good_region else "" + for ident in [prefix+"x_center_of_mass", prefix+"y_center_of_mass", prefix+"x_rms", prefix+"y_rms"]: + child = cam_server.stream.getChild(ident) + av = create_averager(child, number_images, interval) + av.monitored = async + ret.append(av) + return ret + +def wait_cam_server_background(background, timeout = 10000): + start = time.time() + while True: + processing_parameters = cam_server.getProcessingParameters() + if (processing_parameters is not None) and (str(background) == processing_parameters["image_background"]): + return + if (time.time()-start) > timeout/1000: + raise Exception("Timeout waiting for camera server background: " + str(background)) + time.sleep(0.01) + + +def get_camera_type(camera_name): + if "LCAM" in camera_name: return "LASER" + if "DSCR" in camera_name or \ + "DSRM" in camera_name or \ + "DLAC" in camera_name: return "ELECTRONS" + if "PROF" in camera_name or \ + "PPRM" in camera_name or \ + "PSSS" in camera_name or \ + "PSCR" in camera_name or \ + "PSRD" in camera_name: return "PHOTONICS" + return "UNKNOWN" + + +################################################################################################### +# Camera scans +################################################################################################### + +# source = "server", "camtool", "bpm" or "direct" +def setup_camera_scan(): + global source, camera_name, bpm_name, number_images, use_background, multiple_background, number_backgrounds, dry_run + if not is_laser_on(1) and not is_laser_on(2): + raise Exception("Both bunches are on delay") + save_laser_state() + multiple_background = use_background and multiple_background + if source == "server": + cam_server.start(camera_name + "_sp", use_screen_panel_stream) + if use_background: + if not dry_run: + laser_off() + bg=cam_server.captureBackground(1 if multiple_background else number_backgrounds) + cam_server.setBackgroundSubtraction(True) + if not multiple_background: wait_cam_server_background(bg) + else: + cam_server.setBackgroundSubtraction(False) + + elif source == "camtool": + #kill_camtool() + check_camtool() + if use_background: + if not dry_run: + laser_off() + if not multiple_background: + camtool.stop() + camtool.grabBackground(camera_name, number_backgrounds) + camtool.start(camera_name, 0, use_background, None, 0.0, None) + else: + if source == "bpm": + run("Devices/BpmStats") + add_device(BpmStats("image_stats", bpm_name), True) + multiple_background = False + use_background = False + else: + run("Devices/ImageStats") + add_device(ImageStats("image_stats", camera_name), True) + add_device(image_stats.source, True) + image_stats.enableBackground(use_background) + if use_background: + laser_off() + if not multiple_background: + image_stats.grabBackground(number_backgrounds) + image_stats.setNumberOfImages(max(number_images,1)) + + if not multiple_background: + if not dry_run: + #laser_on() + restore_laser_state() + +def before_sample_camera_scan(): + global source, camera_name, number_images, use_background, multiple_background, number_backgrounds, dry_run + if source == "server": + if multiple_background: + bg = cam_server.captureBackground(number_backgrounds) + wait_cam_server_background(bg) + if not dry_run: + #laser_on() + restore_laser_state() + wait_cam_server_message(number_images) + elif source == "camtool": + if multiple_background: + camtool.stop() + camtool.grabBackground(camera_name, number_backgrounds) + camtool.start(camera_name, 0, use_background, None, 0.0, None) + if not dry_run: + #laser_on() + restore_laser_state() + wait_camtool_message(number_images) #Wait filing the averager cache + else: + if multiple_background: + image_stats.grabBackground(number_backgrounds) + #laser_on() + restore_laser_state() + image_stats.update() + +def after_sample_camera_scan(): + if multiple_background: + if not dry_run: + laser_off() + +def get_camera_scan_sensors(): + global source, camera_name, number_images, use_background, multiple_background, number_backgrounds, dry_run + if source == "server": + sensors = get_cam_server_stats(number_images, good_region=use_good_region) + if plot_image: + sensors.append(cam_server.getDataMatrix()) + elif source == "camtool": + sensors = get_camtool_stats(number_images, good_region=use_good_region) + if plot_image: + sensors.append(camtool.getDataMatrix()) + else: + sensors = [image_stats.com_x_mean, image_stats.com_y_mean, image_stats.com_x_stdev, image_stats.com_y_stdev] + if plot_image and (source == "direct"): + sensors.append(image_stats.source.getDataMatrix()) + return sensors + +def end_camera_scan(): + global source, camera_name, number_images, use_background, multiple_background, number_backgrounds, dry_run + #if source == "server": cam_server.stop() + #elif source == "camtool": camtool.stop() + #elif source == "camtool": camtool.stop() + #else: image_stats.stop() + if not dry_run: + restore_laser_state() + +################################################################################################### +#CAS +################################################################################################### + +if get_context().isServerEnabled(): + #CAS.setServerPort(5062) + add_device(EpicsServerUrl("epics_server_url_old", "PSHELL_OP:SERVER_URL"), True) #TODO: Change dependencies to "SF-PSHELL_OP:SERVER_URL and remove + add_device(EpicsServerUrl("epics_server_url", "SF-PSHELL_OP:SERVER_URL"), True) + add_device(EpicsServerState("epics_server_state", "SF-PSHELL_OP:STATE"), True) + add_device(EpicsCmdAPI("epics_cmd", "SF-PSHELL_OP:CMD", as_string=False), True) + add_device(EpicsCmdAPI("epics_cmd_bg", "SF-PSHELL_OP:CMD_BG", as_string=False, background=True), True) + add_device(EpicsCmdAPI("epics_cmd_str", "SF-PSHELL_OP:CMD_STR", as_string=True), True) + add_device(EpicsCmdAPI("epics_cmd_str_bg", "SF-PSHELL_OP:CMD_STR_BG", as_string=True, background=True), True) + + + +################################################################################################### +#background run +################################################################################################### +test_bg_scan_state = State.Ready +test_bg_scan_result = None +und_scan_global_state = State.Ready +und_scan_global_result = None + \ No newline at end of file diff --git a/script/test/TestBsreadCamera.py b/script/test/TestBsreadCamera.py index 4b510c9..7d3e33e 100644 --- a/script/test/TestBsreadCamera.py +++ b/script/test/TestBsreadCamera.py @@ -11,6 +11,7 @@ CAMERA = "S10BC02-DSRM310" CAMERA = "SARBD02-DSCR051" CAMERA = "SATOP21-PMOS127-1D" CAMERA = "SATBD01-DSCR210" +CAMERA = "SATOP31-PMOS132-2D" CAMERA_URL = caget(CAMERA + ":BSREADCONFIG").replace("tcp://daq", "tcp://") #CAMERA_URL= "tcp://sf-sioc-cs-83:9020" #sCAMERA_URL= "tcp://sf-daqsync-17:9002" diff --git a/script/test/TestWscData.py b/script/test/TestWscData.py new file mode 100644 index 0000000..b5a9c57 --- /dev/null +++ b/script/test/TestWscData.py @@ -0,0 +1,23 @@ +run("Diagnostics/WSCdata") +run("Devices/Elements") + +ws = "SINDI01-DWSC090" + + +current_state = {} +blms = WSC_data.get(ws, {})["BLM"] + +for blm in blms: + current_state[blm] = is_blm_enabled(blm) + + +for blm, state in current_state.items(): + if state != (False, False): + #set_blm_enabled(False, name) + print "Disable: ", blm + +for blm, state in current_state.items(): + if state != (False, False): + #set_blm_enabled(state, blm) + print "Restore: ", blm, state + diff --git a/script/test/test.py b/script/test/test.py new file mode 100644 index 0000000..4a29312 --- /dev/null +++ b/script/test/test.py @@ -0,0 +1,8 @@ +import ch.psi.pshell.epics.Positioner as Positioner +import ch.psi.pshell.epics.ChannelDouble as ChannelDouble +import_py("CPython/hfitoff", "hfitoff") +import_py("CPython/extremum", "extremum") + +fit_amplitude, fit_x_deg, fit_offset, x_max, fit_x, fit_y = hfitoff(y_array, x_array) + +error_bar = mean([val.stdev for val in r.getReadable(0)]) diff --git a/script/test/test_bg_scan.py b/script/test/test_bg_scan.py new file mode 100644 index 0000000..7aba4a0 --- /dev/null +++ b/script/test/test_bg_scan.py @@ -0,0 +1,12 @@ +test_bg_scan_state.assertReady() +test_bg_scan_state = State.Busy +test_bg_scan_result = None + +try: + caput("STATS:TESTVALUE4", 11) + test_bg_scan_result = "Ok" +except: + test_bg_scan_result = str(sys.exc_info()[1]) +finally: + #Make sure add this in the finally, otherwise you may get blocked + test_bg_scan_state = State.Ready diff --git a/script/test/test_daqbuf.py b/script/test/test_daqbuf.py new file mode 100644 index 0000000..50f1926 --- /dev/null +++ b/script/test/test_daqbuf.py @@ -0,0 +1,16 @@ +from java.util import Date +from java.text import SimpleDateFormat + +channel = "ARS07-CECL-DPCT:BIN-PCT-STAT0-BIN" +bins = 0 +time_range = 30 + +now = System.currentTimeMillis() +fmt = SimpleDateFormat("yyyy-MM-dd HH:mm:ss") +start = fmt.format(Date(now_ms - time_range * 1000 )) +end = fmt.format(Date(now)) + +set_exec_pars(reset=True) # A different file on each time +filename = get_exec_pars().path +d=Daqbuf(None, "sls-archiver") +d.saveQuery(filename, channel, start, end, bins) diff --git a/script/test/test_daqbuf_nested.py b/script/test/test_daqbuf_nested.py new file mode 100644 index 0000000..31b3ae3 --- /dev/null +++ b/script/test/test_daqbuf_nested.py @@ -0,0 +1,2 @@ +run("test/test_daqbuf") +run("test/test_daqbuf") \ No newline at end of file diff --git a/script/test/test_data-txt.py b/script/test/test_data-txt.py new file mode 100644 index 0000000..1708850 --- /dev/null +++ b/script/test/test_data-txt.py @@ -0,0 +1,6 @@ +#set_exec_pars(format="txt") +data2d = [ [1.0, 2.0, 3.0, 4.0, 5.0], [2.0, 3.0, 4.0, 5.0, 6.0, ], [3.0, 4.0, 5.0, 6.0, 7.0]] + +time.sleep(10.0) +plot(data2d) +set_return(True) \ No newline at end of file diff --git a/script/test/test_data_txt.py b/script/test/test_data_txt.py new file mode 100644 index 0000000..9882474 --- /dev/null +++ b/script/test/test_data_txt.py @@ -0,0 +1,6 @@ +#set_exec_pars(format="txt") +data2d = [ [1.0, 2.0, 3.0, 4.0, 5.0], [2.0, 3.0, 4.0, 5.0, 6.0, ], [3.0, 4.0, 5.0, 6.0, 7.0]] + + +plot(data2d) +set_return(True) \ No newline at end of file diff --git a/script/test/test_nested.py b/script/test/test_nested.py new file mode 100644 index 0000000..4806008 --- /dev/null +++ b/script/test/test_nested.py @@ -0,0 +1,10 @@ +run("test/test_data_txt") +time.sleep(0.5) +run("test/test_data_txt") +time.sleep(0.5) +run("test/test_data_txt") +time.sleep(0.5) +run("test/test_data_txt") +time.sleep(0.5) +run("test/test_data_txt") +set_return(True) \ No newline at end of file